tol-sdk 1.6.36__py3-none-any.whl → 1.6.37__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.
@@ -0,0 +1,6 @@
1
+ # SPDX-FileCopyrightText: 2025 Genome Research Ltd.
2
+ #
3
+ # SPDX-License-Identifier: MIT
4
+
5
+ from .action import Action # noqa
6
+ from .upsert_action import UpsertAction # noqa
tol/actions/action.py ADDED
@@ -0,0 +1,31 @@
1
+ # SPDX-FileCopyrightText: 2025 Genome Research Ltd.
2
+ #
3
+ # SPDX-License-Identifier: MIT
4
+
5
+ from __future__ import annotations
6
+
7
+ from abc import ABC, abstractmethod
8
+ from typing import Any
9
+
10
+ from ..core import DataSource
11
+
12
+
13
+ class Action(ABC):
14
+ """
15
+ The central class for running local actions.
16
+ """
17
+
18
+ @abstractmethod
19
+ def run(
20
+ self,
21
+ datasource: DataSource,
22
+ ids: list[str],
23
+ object_type: str,
24
+ params: dict[str, Any] | None = None
25
+ ) -> tuple[dict[str, bool], int]:
26
+ """
27
+ Run the action on the given IDs and return status in
28
+ format ({'success': True}, 200).
29
+ """
30
+
31
+ pass
@@ -0,0 +1,56 @@
1
+ # SPDX-FileCopyrightText: 2025 Genome Research Ltd.
2
+ #
3
+ # SPDX-License-Identifier: MIT
4
+
5
+ from __future__ import annotations
6
+
7
+ from typing import Any
8
+
9
+ from .action import Action
10
+ from ..core import DataSource
11
+
12
+
13
+ class UpsertAction(Action):
14
+ """
15
+ The central class for running local actions.
16
+ """
17
+
18
+ def __init__(self):
19
+ super().__init__()
20
+
21
+ def run(
22
+ self,
23
+ datasource: DataSource,
24
+ ids: list[str],
25
+ object_type: str,
26
+ params: dict[str, Any] | None = None
27
+ ) -> tuple[dict[str, bool], int]:
28
+
29
+ data_objects = self.__convert_to_data_objects(
30
+ datasource=datasource,
31
+ ids=ids,
32
+ object_type=object_type,
33
+ params=params
34
+ )
35
+
36
+ try:
37
+ datasource.upsert_batch(object_type=object_type, objects=data_objects)
38
+ return {'success': True}, 200
39
+ except Exception as e:
40
+ return {'error': str(e)}, 500
41
+
42
+ def __convert_to_data_objects(
43
+ self,
44
+ datasource: DataSource,
45
+ ids: list[str],
46
+ object_type: str,
47
+ params: dict[str, Any] | None = None
48
+ ) -> Any:
49
+ CoreDataObject = datasource.data_object_factory # noqa N806
50
+
51
+ for id_ in ids:
52
+ yield CoreDataObject(
53
+ type_=object_type,
54
+ id_=id_,
55
+ attributes=params
56
+ )
tol/api_base/action.py CHANGED
@@ -4,6 +4,7 @@
4
4
 
5
5
  from __future__ import annotations
6
6
 
7
+ import importlib
7
8
  import typing
8
9
  from datetime import datetime
9
10
  from typing import Any
@@ -151,31 +152,79 @@ def action_blueprint(
151
152
  else {}
152
153
  )
153
154
 
154
- flow_params = {
155
- 'extra_params': {
155
+ if action.flow_name:
156
+ flow_params = {
157
+ 'extra_params': {
158
+ **params,
159
+ **action_params,
160
+ },
161
+ 'user_id': user_id,
162
+ 'object_type': object_type,
163
+ 'ids': ids
164
+ }
165
+
166
+ flow_run_id, flow_run_name = __insert_flow_run(
167
+ action,
168
+ flow_params,
169
+ user_id
170
+ )
171
+
172
+ user_action_params = {
156
173
  **params,
157
174
  **action_params,
158
- },
159
- 'user_id': user_id,
160
- 'object_type': object_type,
161
- 'ids': ids
162
- }
163
-
164
- flow_run_id, flow_run_name = __insert_flow_run(
165
- action,
166
- flow_params,
167
- user_id
168
- )
175
+ 'ids': ids,
176
+ 'flow_run_id': flow_run_id,
177
+ 'flow_run_name': flow_run_name
178
+ }
169
179
 
170
- user = sql_ds.get_one('user', user_id)
180
+ elif action.class_name:
181
+ # Try to import the class from tol.actions first, then fall back to main.actions
182
+ action_class = None
183
+ try:
184
+ tol_actions_module = importlib.import_module('tol.actions')
185
+ if hasattr(tol_actions_module, action.class_name):
186
+ action_class = getattr(tol_actions_module, action.class_name)
187
+
188
+ if action_class is None:
189
+ main_actions_module = importlib.import_module('main.actions')
190
+ if hasattr(main_actions_module, action.class_name):
191
+ action_class = getattr(main_actions_module, action.class_name)
192
+
193
+ except ImportError:
194
+ raise DataSourceError(
195
+ 'Action Class Import Error',
196
+ 'Class not found in tol.actions or main.actions',
197
+ 500
198
+ )
199
+
200
+ if action_class is None:
201
+ raise DataSourceError(
202
+ 'Action Class Not Found',
203
+ f'Action class "{action.class_name}" not found in tol.actions or main.actions',
204
+ 404
205
+ )
206
+
207
+ class_params = {**action_params, **params}
208
+
209
+ action_instance = action_class()
210
+ status = action_instance.run(ids=ids, params=class_params,
211
+ object_type=object_type, datasource=sql_ds)
212
+
213
+ user_action_params = {
214
+ **params,
215
+ **action_params,
216
+ 'ids': ids,
217
+ 'status': status
218
+ }
171
219
 
172
- user_action_params = {
173
- **params,
174
- **action_params,
175
- 'ids': ids,
176
- 'flow_run_id': flow_run_id,
177
- 'flow_run_name': flow_run_name
178
- }
220
+ else:
221
+ raise DataSourceError(
222
+ 'Invalid Action',
223
+ 'No Actions are defined',
224
+ 400
225
+ )
226
+
227
+ user = sql_ds.get_one('user', user_id)
179
228
 
180
229
  user_action = sql_ds.data_object_factory(
181
230
  'user_action',
tol/sql/sql_datasource.py CHANGED
@@ -202,32 +202,35 @@ class SqlDataSource(
202
202
  )
203
203
  sorter = self.__sorter_factory(sort_by)
204
204
  in_session = self.__get_sqla_session(session)
205
- total_count = self.__db.count(
206
- tablename,
207
- in_session,
208
- filters=database_filter
209
- )
210
- models = self.__get_list_page_models(
211
- tablename,
212
- database_filter,
213
- page_number,
214
- page_size,
215
- sorter,
216
- in_session,
217
- requested_relationships=self.__format_requested_relationships(
218
- object_type,
219
- requested_fields
220
- ),
221
- )
222
- converter = self.__get_converter(
223
- requested_fields=requested_fields
224
- )
225
- return_list = list(
226
- converter.convert_iterable(models)
227
- )
228
- if session is None:
205
+ try:
206
+ total_count = self.__db.count(
207
+ tablename,
208
+ in_session,
209
+ filters=database_filter
210
+ )
211
+ models = self.__get_list_page_models(
212
+ tablename,
213
+ database_filter,
214
+ page_number,
215
+ page_size,
216
+ sorter,
217
+ in_session,
218
+ requested_relationships=self.__format_requested_relationships(
219
+ object_type,
220
+ requested_fields
221
+ ),
222
+ )
223
+ converter = self.__get_converter(
224
+ requested_fields=requested_fields
225
+ )
226
+ return_list = list(
227
+ converter.convert_iterable(models)
228
+ )
229
+ if session is None:
230
+ in_session.close()
231
+ return return_list, total_count
232
+ except KeyError:
229
233
  in_session.close()
230
- return return_list, total_count
231
234
 
232
235
  def get_list(
233
236
  self,
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: tol-sdk
3
- Version: 1.6.36
3
+ Version: 1.6.37
4
4
  Summary: SDK for interaction with ToL, Sanger and external services
5
5
  Author-email: ToL Platforms Team <tol-platforms@sanger.ac.uk>
6
6
  License: MIT
@@ -1,8 +1,11 @@
1
1
  certs/cacert.pem,sha256=VBU2YEgoq_W2VrRC9IYcMoZuRzO96nwmcHBep2xt_l0,199181
2
2
  tol/__init__.py,sha256=0WL4ZHy0Kpa-QZUXJDSu0af690J4gotyQN5wqbk6Zf0,85
3
3
  tol/markdown.py,sha256=X-ooYUYLkkVS8DyBHYib8d2QBBNMPlBP5_ZQz8-mAYc,570
4
+ tol/actions/__init__.py,sha256=xOj2kvRYv2GWQLqrpL_xhwZUZDwtOBnxb5CZ9qmP-pk,169
5
+ tol/actions/action.py,sha256=HlfUsfVGd2vuNAwD_01yo1i32nh6UNrt_ytcY2ladgM,651
6
+ tol/actions/upsert_action.py,sha256=DnSz1LhHibF0WcK6Qht5eLIGi3PPXc6GSRsd8Y2dZBE,1366
4
7
  tol/api_base/__init__.py,sha256=xv9kkAyb1Q5vhKgq6f-JpY7lIAla51U-gIpA5U1OfkA,312
5
- tol/api_base/action.py,sha256=GYjc9ZIqcqJ8DhLWV83cB55R_6SQRoCESlUDL7-EMLc,4676
8
+ tol/api_base/action.py,sha256=l3MzD3jSDdYiZs-HCT4YEsXkp34X26k6yWugXrRB2XU,6575
6
9
  tol/api_base/blueprint.py,sha256=k7so2is91-oHO41a3o0dhkXg4_xfmwQX9AaGzMZhzTY,18286
7
10
  tol/api_base/controller.py,sha256=nAN7RvGFq7_fMibVTR4iGf4QXPuEYGmxfjyxihfMHqE,26556
8
11
  tol/api_base/pipeline_steps.py,sha256=lz888M2cF-5z-EkGK_sWfZf1otnYRmgnNuC0WUqI-po,5667
@@ -292,7 +295,7 @@ tol/sql/relationship.py,sha256=8biXecUuJ6KKGjgB9fIIEKyDvcHjdG76iotb-x8LG8Q,2890
292
295
  tol/sql/session.py,sha256=VmqTegr4L2X2zvaOJCpwSrkVRx8fc1RVL0drkL2MXu8,806
293
296
  tol/sql/sort.py,sha256=ENrjHGgj4fZtXKmkdlkv1HRi1X14SVlcl-tp8Pu7G0k,2553
294
297
  tol/sql/sql_converter.py,sha256=WtqdAT9PPuwBn8q3ZO-e_uAqBUP0cYU2seowBGUVT0Q,5282
295
- tol/sql/sql_datasource.py,sha256=68L7xF3PiEMXE5fxC0fndOkxkOoc4EinVPPcQmtGyLY,17274
298
+ tol/sql/sql_datasource.py,sha256=xP6-ZTEfF6BXLvGs_18tea7vRJGoT_Eg1lh7XTEutWQ,17447
296
299
  tol/sql/action/__init__.py,sha256=T1zAsCza_lvsNtXF1ecSLt9OFGup8tGnIs68YylBmXI,142
297
300
  tol/sql/action/factory.py,sha256=HkareJp_57ud0_Bdd9Kwz3_Rnq2l211sGJgftohFAHg,3589
298
301
  tol/sql/auth/__init__.py,sha256=e3JuwugXmXobklqZ1Mt1w03qPgb1WdUaJVM7oblzHyk,202
@@ -321,9 +324,9 @@ tol/validators/__init__.py,sha256=XXwCt8JPQ5-w2kN1bVjJPLXbS9F4s1nJUnY9jaKdmVk,27
321
324
  tol/validators/allowed_keys.py,sha256=BJMomJtaQdxsdGsueDtLewv75TlwdIXiQipLGFcJ7_c,1331
322
325
  tol/validators/allowed_values.py,sha256=yJ5SdiUlV7PSKORtsBJ9hYSqwvlx_esbFmFL_Gxh-p4,2262
323
326
  tol/validators/unique_values.py,sha256=stI-1i006WEbERcjSMapRggJkEF-RFDzw2uUtXBAE_M,1885
324
- tol_sdk-1.6.36.dist-info/licenses/LICENSE,sha256=RF9Jacy-9BpUAQQ20INhTgtaNBkmdTolYCHtrrkM2-8,1077
325
- tol_sdk-1.6.36.dist-info/METADATA,sha256=G3rnsFcEIx7d74X6o1q4ukuUlc4CySHpo__cDNYA8sg,3073
326
- tol_sdk-1.6.36.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
327
- tol_sdk-1.6.36.dist-info/entry_points.txt,sha256=jH3HfTwxjzog7E3lq8CKpUWGIRY9FSXbyL6CpUmv6D0,36
328
- tol_sdk-1.6.36.dist-info/top_level.txt,sha256=PwKMQLphyZNvagBoriVbl8uwHXQl8IC1niawVG0iXMM,10
329
- tol_sdk-1.6.36.dist-info/RECORD,,
327
+ tol_sdk-1.6.37.dist-info/licenses/LICENSE,sha256=RF9Jacy-9BpUAQQ20INhTgtaNBkmdTolYCHtrrkM2-8,1077
328
+ tol_sdk-1.6.37.dist-info/METADATA,sha256=2C34dKqCV06qMbCP73eObpby_rO-56dD9QMgSTrQHzU,3073
329
+ tol_sdk-1.6.37.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
330
+ tol_sdk-1.6.37.dist-info/entry_points.txt,sha256=jH3HfTwxjzog7E3lq8CKpUWGIRY9FSXbyL6CpUmv6D0,36
331
+ tol_sdk-1.6.37.dist-info/top_level.txt,sha256=PwKMQLphyZNvagBoriVbl8uwHXQl8IC1niawVG0iXMM,10
332
+ tol_sdk-1.6.37.dist-info/RECORD,,