dara-core 1.16.21__py3-none-any.whl → 1.16.22__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.
- dara/core/__init__.py +1 -0
- dara/core/interactivity/__init__.py +2 -0
- dara/core/interactivity/actions.py +65 -0
- dara/core/interactivity/derived_variable.py +1 -1
- dara/core/internal/tasks.py +13 -1
- {dara_core-1.16.21.dist-info → dara_core-1.16.22.dist-info}/METADATA +10 -10
- {dara_core-1.16.21.dist-info → dara_core-1.16.22.dist-info}/RECORD +10 -10
- {dara_core-1.16.21.dist-info → dara_core-1.16.22.dist-info}/LICENSE +0 -0
- {dara_core-1.16.21.dist-info → dara_core-1.16.22.dist-info}/WHEEL +0 -0
- {dara_core-1.16.21.dist-info → dara_core-1.16.22.dist-info}/entry_points.txt +0 -0
dara/core/__init__.py
CHANGED
|
@@ -20,6 +20,7 @@ from __future__ import annotations
|
|
|
20
20
|
from pydantic import BaseModel
|
|
21
21
|
|
|
22
22
|
from dara.core.interactivity.actions import (
|
|
23
|
+
ActionCtx,
|
|
23
24
|
DownloadContent,
|
|
24
25
|
DownloadContentImpl,
|
|
25
26
|
DownloadVariable,
|
|
@@ -45,6 +46,7 @@ from dara.core.interactivity.url_variable import UrlVariable
|
|
|
45
46
|
|
|
46
47
|
__all__ = [
|
|
47
48
|
'action',
|
|
49
|
+
'ActionCtx',
|
|
48
50
|
'AnyVariable',
|
|
49
51
|
'AnyDataVariable',
|
|
50
52
|
'DataVariable',
|
|
@@ -52,6 +52,7 @@ from dara.core.base_definitions import (
|
|
|
52
52
|
AnnotatedAction,
|
|
53
53
|
)
|
|
54
54
|
from dara.core.base_definitions import DaraBaseModel as BaseModel
|
|
55
|
+
from dara.core.base_definitions import TaskProgressUpdate
|
|
55
56
|
from dara.core.interactivity.data_variable import DataVariable
|
|
56
57
|
from dara.core.internal.download import generate_download_code
|
|
57
58
|
from dara.core.internal.registry_lookup import RegistryLookup
|
|
@@ -1192,6 +1193,70 @@ class ActionCtx:
|
|
|
1192
1193
|
"""
|
|
1193
1194
|
return await DownloadVariable(variable=variable, file_name=file_name, type=type).execute(self)
|
|
1194
1195
|
|
|
1196
|
+
async def run_task(
|
|
1197
|
+
self,
|
|
1198
|
+
func: Callable,
|
|
1199
|
+
args: Union[List[Any], None] = None,
|
|
1200
|
+
kwargs: Union[Dict[str, Any], None] = None,
|
|
1201
|
+
on_progress: Optional[Callable[[TaskProgressUpdate], Union[None, Awaitable[None]]]] = None,
|
|
1202
|
+
):
|
|
1203
|
+
"""
|
|
1204
|
+
Run a calculation as a task in a separate process. Recommended for CPU intensive tasks.
|
|
1205
|
+
Returns the result of the task function.
|
|
1206
|
+
|
|
1207
|
+
Note that the function must be defined in a separate module as configured in `task_module` field of the
|
|
1208
|
+
configuration builder. This is because Dara spawns separate worker processes only designed to run
|
|
1209
|
+
functions from that designated module.
|
|
1210
|
+
|
|
1211
|
+
```python
|
|
1212
|
+
from dara.core import ConfigurationBuilder, TaskProgressUpdate, action, ActionCtx, Variable
|
|
1213
|
+
from dara.components import Text, Stack, Button
|
|
1214
|
+
from .my_module import my_task_function
|
|
1215
|
+
|
|
1216
|
+
config = ConfigurationBuilder()
|
|
1217
|
+
config.task_module = 'my_module'
|
|
1218
|
+
|
|
1219
|
+
status = Variable('Not started')
|
|
1220
|
+
|
|
1221
|
+
@action
|
|
1222
|
+
async def my_task(ctx: ActionCtx):
|
|
1223
|
+
async def on_progress(update: TaskProgressUpdate):
|
|
1224
|
+
await ctx.update(status, f'Progress: {update.progress}% - {update.message}')
|
|
1225
|
+
|
|
1226
|
+
try:
|
|
1227
|
+
result = await ctx.run_task(my_task_function, args=[1, 10], on_progress=on_progress)
|
|
1228
|
+
await ctx.update(status, f'Result: {result}')
|
|
1229
|
+
except Exception as e:
|
|
1230
|
+
await ctx.update(status, f'Error: {e}')
|
|
1231
|
+
|
|
1232
|
+
def task_page():
|
|
1233
|
+
return Stack(Text('Status display:'), Text(text=status), Button('Run', onclick=my_task()))
|
|
1234
|
+
|
|
1235
|
+
config.add_page(name='task', content=task_page())
|
|
1236
|
+
```
|
|
1237
|
+
|
|
1238
|
+
:param func: the function to run as a task
|
|
1239
|
+
:param args: the arguments to pass to the function
|
|
1240
|
+
:param kwargs: the keyword arguments to pass to the function
|
|
1241
|
+
:param on_progress: a callback to receive progress updates
|
|
1242
|
+
"""
|
|
1243
|
+
from dara.core.internal.registries import utils_registry
|
|
1244
|
+
from dara.core.internal.tasks import Task, TaskManager
|
|
1245
|
+
|
|
1246
|
+
task_mgr: TaskManager = utils_registry.get('TaskManager')
|
|
1247
|
+
|
|
1248
|
+
task = Task(func=func, args=args, kwargs=kwargs, on_progress=on_progress)
|
|
1249
|
+
pending_task = await task_mgr.run_task(task)
|
|
1250
|
+
|
|
1251
|
+
# Run until completion
|
|
1252
|
+
await pending_task.event.wait()
|
|
1253
|
+
|
|
1254
|
+
# Raise exception if there was one
|
|
1255
|
+
if pending_task.error:
|
|
1256
|
+
raise pending_task.error
|
|
1257
|
+
|
|
1258
|
+
return pending_task.result
|
|
1259
|
+
|
|
1195
1260
|
async def execute_action(self, action: ActionImpl):
|
|
1196
1261
|
"""
|
|
1197
1262
|
Execute a given action.
|
|
@@ -90,7 +90,7 @@ class DerivedVariable(NonDataVariable, Generic[VariableType]):
|
|
|
90
90
|
|
|
91
91
|
def __init__(
|
|
92
92
|
self,
|
|
93
|
-
func: Callable[..., VariableType],
|
|
93
|
+
func: Callable[..., VariableType] | Callable[..., Awaitable[VariableType]],
|
|
94
94
|
variables: List[AnyVariable],
|
|
95
95
|
cache: Optional[CacheArgType] = Cache.Type.GLOBAL,
|
|
96
96
|
run_as_task: bool = False,
|
dara/core/internal/tasks.py
CHANGED
|
@@ -17,7 +17,7 @@ limitations under the License.
|
|
|
17
17
|
|
|
18
18
|
import inspect
|
|
19
19
|
import math
|
|
20
|
-
from typing import Any, Callable, Dict, List, Optional, Union
|
|
20
|
+
from typing import Any, Awaitable, Callable, Dict, List, Optional, Union, overload
|
|
21
21
|
|
|
22
22
|
from anyio import (
|
|
23
23
|
CancelScope,
|
|
@@ -70,6 +70,7 @@ class Task(BaseTask):
|
|
|
70
70
|
notify_channels: Optional[List[str]] = None,
|
|
71
71
|
cache_key: Optional[str] = None,
|
|
72
72
|
task_id: Optional[str] = None,
|
|
73
|
+
on_progress: Optional[Callable[[TaskProgressUpdate], Union[None, Awaitable[None]]]] = None,
|
|
73
74
|
):
|
|
74
75
|
"""
|
|
75
76
|
:param func: The function to execute within the process
|
|
@@ -87,6 +88,7 @@ class Task(BaseTask):
|
|
|
87
88
|
self.notify_channels = notify_channels if notify_channels is not None else []
|
|
88
89
|
self.cache_key = cache_key
|
|
89
90
|
self.reg_entry = reg_entry
|
|
91
|
+
self.on_progress = on_progress
|
|
90
92
|
|
|
91
93
|
super().__init__(task_id)
|
|
92
94
|
|
|
@@ -359,6 +361,14 @@ class TaskManager:
|
|
|
359
361
|
self.ws_manager = ws_manager
|
|
360
362
|
self.store = store
|
|
361
363
|
|
|
364
|
+
@overload
|
|
365
|
+
async def run_task(self, task: PendingTask, ws_channel: Optional[str] = None) -> Any:
|
|
366
|
+
...
|
|
367
|
+
|
|
368
|
+
@overload
|
|
369
|
+
async def run_task(self, task: BaseTask, ws_channel: Optional[str] = None) -> PendingTask:
|
|
370
|
+
...
|
|
371
|
+
|
|
362
372
|
async def run_task(self, task: BaseTask, ws_channel: Optional[str] = None):
|
|
363
373
|
"""
|
|
364
374
|
Run a task and store it in the tasks dict
|
|
@@ -504,6 +514,8 @@ class TaskManager:
|
|
|
504
514
|
'message': message.message,
|
|
505
515
|
}
|
|
506
516
|
)
|
|
517
|
+
if isinstance(task, Task) and task.on_progress:
|
|
518
|
+
await run_user_handler(task.on_progress, args=(message,))
|
|
507
519
|
elif isinstance(message, TaskResult):
|
|
508
520
|
# Resolve the pending task related to the result
|
|
509
521
|
if message.task_id in self.tasks:
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: dara-core
|
|
3
|
-
Version: 1.16.
|
|
3
|
+
Version: 1.16.22
|
|
4
4
|
Summary: Dara Framework Core
|
|
5
5
|
Home-page: https://dara.causalens.com/
|
|
6
6
|
License: Apache-2.0
|
|
@@ -20,10 +20,10 @@ Requires-Dist: async-asgi-testclient (>=1.4.11,<2.0.0)
|
|
|
20
20
|
Requires-Dist: certifi (>=2024.7.4)
|
|
21
21
|
Requires-Dist: click (==8.1.3)
|
|
22
22
|
Requires-Dist: colorama (>=0.4.6,<0.5.0)
|
|
23
|
-
Requires-Dist: create-dara-app (==1.16.
|
|
23
|
+
Requires-Dist: create-dara-app (==1.16.22)
|
|
24
24
|
Requires-Dist: croniter (>=1.0.15,<3.0.0)
|
|
25
25
|
Requires-Dist: cryptography (>=42.0.4)
|
|
26
|
-
Requires-Dist: dara-components (==1.16.
|
|
26
|
+
Requires-Dist: dara-components (==1.16.22) ; extra == "all"
|
|
27
27
|
Requires-Dist: exceptiongroup (>=1.1.3,<2.0.0)
|
|
28
28
|
Requires-Dist: fastapi (>=0.115.0,<0.116.0)
|
|
29
29
|
Requires-Dist: fastapi_vite_dara (==0.4.0)
|
|
@@ -54,7 +54,7 @@ Description-Content-Type: text/markdown
|
|
|
54
54
|
|
|
55
55
|
# Dara Application Framework
|
|
56
56
|
|
|
57
|
-
<img src="https://github.com/causalens/dara/blob/v1.16.
|
|
57
|
+
<img src="https://github.com/causalens/dara/blob/v1.16.22/img/dara_light.svg?raw=true">
|
|
58
58
|
|
|
59
59
|

|
|
60
60
|
[](https://www.apache.org/licenses/LICENSE-2.0)
|
|
@@ -99,7 +99,7 @@ source .venv/bin/activate
|
|
|
99
99
|
dara start
|
|
100
100
|
```
|
|
101
101
|
|
|
102
|
-

|
|
103
103
|
|
|
104
104
|
Note: `pip` installation uses [PEP 660](https://peps.python.org/pep-0660/) `pyproject.toml`-based editable installs which require `pip >= 21.3` and `setuptools >= 64.0.0`. You can upgrade both with:
|
|
105
105
|
|
|
@@ -116,9 +116,9 @@ Explore some of our favorite apps - a great way of getting started and getting t
|
|
|
116
116
|
|
|
117
117
|
| Dara App | Description |
|
|
118
118
|
| -------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
119
|
-
|  | Demonstrates how to use incorporate a LLM chat box into your decision app to understand model insights |
|
|
120
|
+
|  | Demonstrates how to enable the user to interact with plots, trigger actions based on clicks, mouse movements and other interactions with `Bokeh` or `Plotly` plots |
|
|
121
|
+
|  | Demonstrates how to use the `CausalGraphViewer` component to display your graphs or networks, customising the displayed information through colors and tooltips, and updating the page based on user interaction. |
|
|
122
122
|
|
|
123
123
|
Check out our [App Gallery](https://dara.causalens.com/gallery) for more inspiration!
|
|
124
124
|
|
|
@@ -145,9 +145,9 @@ And the supporting UI packages and tools.
|
|
|
145
145
|
- `ui-utils` - miscellaneous utility functions
|
|
146
146
|
- `ui-widgets` - widget components
|
|
147
147
|
|
|
148
|
-
More information on the repository structure can be found in the [CONTRIBUTING.md](https://github.com/causalens/dara/blob/v1.16.
|
|
148
|
+
More information on the repository structure can be found in the [CONTRIBUTING.md](https://github.com/causalens/dara/blob/v1.16.22/CONTRIBUTING.md) file.
|
|
149
149
|
|
|
150
150
|
## License
|
|
151
151
|
|
|
152
|
-
Dara is open-source and licensed under the [Apache 2.0 License](https://github.com/causalens/dara/blob/v1.16.
|
|
152
|
+
Dara is open-source and licensed under the [Apache 2.0 License](https://github.com/causalens/dara/blob/v1.16.22/LICENSE).
|
|
153
153
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
dara/core/__init__.py,sha256=
|
|
1
|
+
dara/core/__init__.py,sha256=Hib2omvNFpEk72wyYMWQrbf18-uKyn4GW8LlcAtBMoI,2111
|
|
2
2
|
dara/core/actions.py,sha256=gARcrrtzYuBAVJUCtuHwpFc6PPVPb7x3ITIISCLw0GA,965
|
|
3
3
|
dara/core/auth/__init__.py,sha256=H0bJoXff5wIRZmHvvQ3y9p5SXA9lM8OuLCGceYGqfb0,851
|
|
4
4
|
dara/core/auth/base.py,sha256=qxmiIzx-n2g4ZWicgxsYtHjiB14AemOWM_GNxcr98mE,3294
|
|
@@ -14,14 +14,14 @@ dara/core/data_utils.py,sha256=5GGz4vk6srLO8HMySiAEk_xZCvmf0SeTTgVi-N4qaKY,12636
|
|
|
14
14
|
dara/core/defaults.py,sha256=UkjWwIbo8GLyn8RZRoD3cJe174-3wHZYzvMB0hQCnMg,4150
|
|
15
15
|
dara/core/definitions.py,sha256=QouD2P2XInW6bqrhPtrfIyDi8i99Au2PTBdWBtgBVrE,16713
|
|
16
16
|
dara/core/http.py,sha256=LR1Kr5Hca-Z6klNl-M8R8Q1eOfFh3hLrjVS3kVrRsKA,4658
|
|
17
|
-
dara/core/interactivity/__init__.py,sha256=
|
|
18
|
-
dara/core/interactivity/actions.py,sha256=
|
|
17
|
+
dara/core/interactivity/__init__.py,sha256=zZp4wO6nHZ_-IzDtlv8D5mjlutn4bckqIiSCaPoCYZw,2326
|
|
18
|
+
dara/core/interactivity/actions.py,sha256=yMw8S11wj4J2HVmDsmedh9D0IZFL9hxw6WGNj7X2f6M,48198
|
|
19
19
|
dara/core/interactivity/any_data_variable.py,sha256=1dLLxLuDErRsgaFPSTXxZHvpVucKKty90twQE6N-_NI,5286
|
|
20
20
|
dara/core/interactivity/any_variable.py,sha256=LOGhbDdYffujlRxF4LR9ZuWdai03R-EXuGsTEJAwfo0,13544
|
|
21
21
|
dara/core/interactivity/condition.py,sha256=q_RDDt-DtZEUQL054Mc7zHyJIJIGACljJ2gOFygCHQc,1309
|
|
22
22
|
dara/core/interactivity/data_variable.py,sha256=pvPOx6SMxHWDxoo5Ea5xqLwrBTrWN68x8lnBiblYSGg,11760
|
|
23
23
|
dara/core/interactivity/derived_data_variable.py,sha256=u2HOts5rtmzK3D1K383YfYYQnb4pHZF3rTu1lfwMpPA,15323
|
|
24
|
-
dara/core/interactivity/derived_variable.py,sha256=
|
|
24
|
+
dara/core/interactivity/derived_variable.py,sha256=x_vdt8hvgubDEISX6GfpR5CS7n2Vxq3oZIkVd8Daiw0,21927
|
|
25
25
|
dara/core/interactivity/filtering.py,sha256=BZsWsQvXPhn6WUoAFpAtgN6hXlGDudPbi4h97Qao2ic,9197
|
|
26
26
|
dara/core/interactivity/loop_variable.py,sha256=EqZX3bMCwKmI2Yu4pQ7TJG9hf3PY2AlAIBLxEzHFbTw,2998
|
|
27
27
|
dara/core/interactivity/non_data_variable.py,sha256=IMH5cNce2O6RUbu4HB_VLT-BBnDnGHr3lp09XU_lWa4,2378
|
|
@@ -59,7 +59,7 @@ dara/core/internal/routing.py,sha256=D2HFfwPKKpDuvvIwXInDWKoq2-zweMVmt4MiVBzorO0
|
|
|
59
59
|
dara/core/internal/scheduler.py,sha256=tKpyN_yhtEepfqfkNTfFep055dl-Lq1_Itte6FTkH9o,12978
|
|
60
60
|
dara/core/internal/settings.py,sha256=ViEni6lVXvbP6Ofb0VoTaWXkI0XajmD-LBpqz1LzwpA,3923
|
|
61
61
|
dara/core/internal/store.py,sha256=kLRDuYEFwqpJMS0CmL5jGmETs645Xcug4jlelJqk5w4,7706
|
|
62
|
-
dara/core/internal/tasks.py,sha256=
|
|
62
|
+
dara/core/internal/tasks.py,sha256=5NdUWGwy11Dd0riPBxiUP9IMb6Is7bfSnD40WLVRFik,25328
|
|
63
63
|
dara/core/internal/utils.py,sha256=b1YYkn8qHl6-GY6cCm2MS1NXRS9j_rElYCKMZOxJgrY,8232
|
|
64
64
|
dara/core/internal/websocket.py,sha256=qeW7KOeJ_FPkpAJNZaVwxIN_DqDv7XK7uyjTxJ8HIno,22043
|
|
65
65
|
dara/core/jinja/index.html,sha256=1gkCFiihXOUH7vp7tT5gH8mKeJB4KqNg394xO3a0usI,1208
|
|
@@ -106,8 +106,8 @@ dara/core/visual/themes/__init__.py,sha256=aM4mgoIYo2neBSw5FRzswsht7PUKjLthiHLmF
|
|
|
106
106
|
dara/core/visual/themes/dark.py,sha256=UQGDooOc8ric73eHs9E0ltYP4UCrwqQ3QxqN_fb4PwY,1942
|
|
107
107
|
dara/core/visual/themes/definitions.py,sha256=nS_gQvOzCt5hTmj74d0_siq_9QWuj6wNuir4VCHy0Dk,2779
|
|
108
108
|
dara/core/visual/themes/light.py,sha256=-Tviq8oEwGbdFULoDOqPuHO0UpAZGsBy8qFi0kAGolQ,1944
|
|
109
|
-
dara_core-1.16.
|
|
110
|
-
dara_core-1.16.
|
|
111
|
-
dara_core-1.16.
|
|
112
|
-
dara_core-1.16.
|
|
113
|
-
dara_core-1.16.
|
|
109
|
+
dara_core-1.16.22.dist-info/LICENSE,sha256=r9u1w2RvpLMV6YjuXHIKXRBKzia3fx_roPwboGcLqCc,10944
|
|
110
|
+
dara_core-1.16.22.dist-info/METADATA,sha256=OaGKDjB2t-bVSdBdPCJCOz3MbS5V_Cqsb9zazY8dh-I,7507
|
|
111
|
+
dara_core-1.16.22.dist-info/WHEEL,sha256=sP946D7jFCHeNz5Iq4fL4Lu-PrWrFsgfLXbbkciIZwg,88
|
|
112
|
+
dara_core-1.16.22.dist-info/entry_points.txt,sha256=H__D5sNIGuPIhVam0DChNL-To5k8Y7nY7TAFz9Mz6cc,139
|
|
113
|
+
dara_core-1.16.22.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|