fractal-server 2.18.6__py3-none-any.whl → 2.19.0__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.
- fractal_server/__init__.py +1 -1
- fractal_server/app/models/security.py +16 -0
- fractal_server/app/models/v2/dataset.py +0 -4
- fractal_server/app/models/v2/job.py +4 -0
- fractal_server/app/models/v2/task.py +0 -1
- fractal_server/app/models/v2/task_group.py +4 -0
- fractal_server/app/models/v2/workflow.py +2 -0
- fractal_server/app/models/v2/workflowtask.py +3 -0
- fractal_server/app/routes/admin/v2/sharing.py +47 -0
- fractal_server/app/routes/admin/v2/task.py +0 -5
- fractal_server/app/routes/admin/v2/task_group_lifecycle.py +6 -0
- fractal_server/app/routes/api/__init__.py +4 -52
- fractal_server/app/routes/api/alive.py +13 -0
- fractal_server/app/routes/api/settings.py +44 -0
- fractal_server/app/routes/api/v2/__init__.py +0 -2
- fractal_server/app/routes/api/v2/_aux_functions_task_lifecycle.py +1 -20
- fractal_server/app/routes/api/v2/dataset.py +9 -8
- fractal_server/app/routes/api/v2/history.py +8 -8
- fractal_server/app/routes/api/v2/images.py +6 -5
- fractal_server/app/routes/api/v2/job.py +10 -9
- fractal_server/app/routes/api/v2/pre_submission_checks.py +3 -3
- fractal_server/app/routes/api/v2/project.py +7 -6
- fractal_server/app/routes/api/v2/sharing.py +17 -9
- fractal_server/app/routes/api/v2/submit.py +5 -3
- fractal_server/app/routes/api/v2/task.py +7 -6
- fractal_server/app/routes/api/v2/task_collection.py +4 -2
- fractal_server/app/routes/api/v2/task_collection_custom.py +2 -2
- fractal_server/app/routes/api/v2/task_collection_pixi.py +4 -2
- fractal_server/app/routes/api/v2/task_group.py +9 -30
- fractal_server/app/routes/api/v2/task_group_lifecycle.py +10 -4
- fractal_server/app/routes/api/v2/task_version_update.py +4 -3
- fractal_server/app/routes/api/v2/workflow.py +10 -9
- fractal_server/app/routes/api/v2/workflow_import.py +14 -45
- fractal_server/app/routes/api/v2/workflowtask.py +7 -11
- fractal_server/app/routes/auth/__init__.py +18 -1
- fractal_server/app/routes/auth/current_user.py +8 -0
- fractal_server/app/routes/auth/users.py +11 -0
- fractal_server/app/routes/aux/_versions.py +42 -0
- fractal_server/app/schemas/user.py +7 -0
- fractal_server/app/schemas/v2/__init__.py +0 -1
- fractal_server/app/schemas/v2/dumps.py +0 -1
- fractal_server/app/schemas/v2/task.py +0 -5
- fractal_server/app/schemas/v2/workflow.py +2 -0
- fractal_server/app/schemas/v2/workflowtask.py +6 -2
- fractal_server/app/security/__init__.py +8 -3
- fractal_server/migrations/versions/18a26fcdea5d_drop_dataset_history.py +41 -0
- fractal_server/migrations/versions/1bf8785755f9_add_description_to_workflow_and_.py +53 -0
- fractal_server/migrations/versions/5fb08bf05b14_drop_taskv2_source.py +36 -0
- fractal_server/migrations/versions/cfd13f7954e7_add_fractal_server_version_to_jobv2_and_.py +52 -0
- fractal_server/migrations/versions/e53dc51fdf93_add_useroauth_is_guest.py +36 -0
- fractal_server/runner/v2/submit_workflow.py +0 -2
- {fractal_server-2.18.6.dist-info → fractal_server-2.19.0.dist-info}/METADATA +2 -2
- {fractal_server-2.18.6.dist-info → fractal_server-2.19.0.dist-info}/RECORD +56 -49
- fractal_server/app/routes/api/v2/status_legacy.py +0 -156
- {fractal_server-2.18.6.dist-info → fractal_server-2.19.0.dist-info}/WHEEL +0 -0
- {fractal_server-2.18.6.dist-info → fractal_server-2.19.0.dist-info}/entry_points.txt +0 -0
- {fractal_server-2.18.6.dist-info → fractal_server-2.19.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -15,7 +15,8 @@ from fractal_server.app.db import get_async_db
|
|
|
15
15
|
from fractal_server.app.models import UserOAuth
|
|
16
16
|
from fractal_server.app.models.v2 import JobV2
|
|
17
17
|
from fractal_server.app.models.v2 import LinkUserProjectV2
|
|
18
|
-
from fractal_server.app.routes.auth import
|
|
18
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
19
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
19
20
|
from fractal_server.app.routes.aux._job import _write_shutdown_file
|
|
20
21
|
from fractal_server.app.routes.aux._runner import _check_shutdown_is_supported
|
|
21
22
|
from fractal_server.app.schemas.v2 import JobRead
|
|
@@ -41,12 +42,12 @@ router = APIRouter()
|
|
|
41
42
|
|
|
42
43
|
@router.get("/job/", response_model=list[JobRead])
|
|
43
44
|
async def get_user_jobs(
|
|
44
|
-
user: UserOAuth = Depends(
|
|
45
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
45
46
|
log: bool = True,
|
|
46
47
|
db: AsyncSession = Depends(get_async_db),
|
|
47
48
|
) -> list[JobRead]:
|
|
48
49
|
"""
|
|
49
|
-
Returns all the jobs
|
|
50
|
+
Returns all the jobs from projects linked to the current user
|
|
50
51
|
"""
|
|
51
52
|
stm = (
|
|
52
53
|
select(JobV2)
|
|
@@ -73,7 +74,7 @@ async def get_user_jobs(
|
|
|
73
74
|
async def get_workflow_jobs(
|
|
74
75
|
project_id: int,
|
|
75
76
|
workflow_id: int,
|
|
76
|
-
user: UserOAuth = Depends(
|
|
77
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
77
78
|
db: AsyncSession = Depends(get_async_db),
|
|
78
79
|
) -> list[JobRead] | None:
|
|
79
80
|
"""
|
|
@@ -100,7 +101,7 @@ async def get_latest_job(
|
|
|
100
101
|
project_id: int,
|
|
101
102
|
workflow_id: int,
|
|
102
103
|
dataset_id: int,
|
|
103
|
-
user: UserOAuth = Depends(
|
|
104
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
104
105
|
db: AsyncSession = Depends(get_async_db),
|
|
105
106
|
) -> JobRead:
|
|
106
107
|
await _get_workflow_check_access(
|
|
@@ -136,7 +137,7 @@ async def read_job(
|
|
|
136
137
|
project_id: int,
|
|
137
138
|
job_id: int,
|
|
138
139
|
show_tmp_logs: bool = False,
|
|
139
|
-
user: UserOAuth = Depends(
|
|
140
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
140
141
|
db: AsyncSession = Depends(get_async_db),
|
|
141
142
|
) -> JobRead | None:
|
|
142
143
|
"""
|
|
@@ -169,7 +170,7 @@ async def read_job(
|
|
|
169
170
|
async def download_job_logs(
|
|
170
171
|
project_id: int,
|
|
171
172
|
job_id: int,
|
|
172
|
-
user: UserOAuth = Depends(
|
|
173
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
173
174
|
db: AsyncSession = Depends(get_async_db),
|
|
174
175
|
) -> StreamingResponse:
|
|
175
176
|
"""
|
|
@@ -200,7 +201,7 @@ async def download_job_logs(
|
|
|
200
201
|
)
|
|
201
202
|
async def get_job_list(
|
|
202
203
|
project_id: int,
|
|
203
|
-
user: UserOAuth = Depends(
|
|
204
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
204
205
|
log: bool = True,
|
|
205
206
|
db: AsyncSession = Depends(get_async_db),
|
|
206
207
|
) -> list[JobRead] | None:
|
|
@@ -234,7 +235,7 @@ async def get_job_list(
|
|
|
234
235
|
async def stop_job(
|
|
235
236
|
project_id: int,
|
|
236
237
|
job_id: int,
|
|
237
|
-
user: UserOAuth = Depends(
|
|
238
|
+
user: UserOAuth = Depends(get_api_user),
|
|
238
239
|
db: AsyncSession = Depends(get_async_db),
|
|
239
240
|
) -> Response:
|
|
240
241
|
"""
|
|
@@ -8,7 +8,7 @@ from pydantic import Field
|
|
|
8
8
|
from fractal_server.app.db import AsyncSession
|
|
9
9
|
from fractal_server.app.db import get_async_db
|
|
10
10
|
from fractal_server.app.models import UserOAuth
|
|
11
|
-
from fractal_server.app.routes.auth import
|
|
11
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
12
12
|
from fractal_server.app.schemas.v2 import HistoryUnitStatus
|
|
13
13
|
from fractal_server.app.schemas.v2 import TaskType
|
|
14
14
|
from fractal_server.app.schemas.v2.sharing import ProjectPermissions
|
|
@@ -34,7 +34,7 @@ async def verify_unique_types(
|
|
|
34
34
|
dataset_id: int,
|
|
35
35
|
workflowtask_id: int,
|
|
36
36
|
query: ImageQuery | None = None,
|
|
37
|
-
user: UserOAuth = Depends(
|
|
37
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
38
38
|
db: AsyncSession = Depends(get_async_db),
|
|
39
39
|
) -> list[str]:
|
|
40
40
|
# Get dataset
|
|
@@ -99,7 +99,7 @@ async def check_non_processed_images(
|
|
|
99
99
|
workflow_id: int,
|
|
100
100
|
workflowtask_id: int,
|
|
101
101
|
filters: NonProcessedImagesPayload,
|
|
102
|
-
user: UserOAuth = Depends(
|
|
102
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
103
103
|
db: AsyncSession = Depends(get_async_db),
|
|
104
104
|
) -> JSONResponse:
|
|
105
105
|
db_workflow_task, db_workflow = await _get_workflow_task_check_access(
|
|
@@ -11,7 +11,8 @@ from fractal_server.app.models import UserOAuth
|
|
|
11
11
|
from fractal_server.app.models.v2 import JobV2
|
|
12
12
|
from fractal_server.app.models.v2 import LinkUserProjectV2
|
|
13
13
|
from fractal_server.app.models.v2 import ProjectV2
|
|
14
|
-
from fractal_server.app.routes.auth import
|
|
14
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
15
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
15
16
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
16
17
|
validate_user_profile,
|
|
17
18
|
)
|
|
@@ -32,7 +33,7 @@ router = APIRouter()
|
|
|
32
33
|
@router.get("/project/", response_model=list[ProjectRead])
|
|
33
34
|
async def get_list_project(
|
|
34
35
|
is_owner: bool = True,
|
|
35
|
-
user: UserOAuth = Depends(
|
|
36
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
36
37
|
db: AsyncSession = Depends(get_async_db),
|
|
37
38
|
) -> list[ProjectV2]:
|
|
38
39
|
"""
|
|
@@ -53,7 +54,7 @@ async def get_list_project(
|
|
|
53
54
|
@router.post("/project/", response_model=ProjectRead, status_code=201)
|
|
54
55
|
async def create_project(
|
|
55
56
|
project: ProjectCreate,
|
|
56
|
-
user: UserOAuth = Depends(
|
|
57
|
+
user: UserOAuth = Depends(get_api_user),
|
|
57
58
|
db: AsyncSession = Depends(get_async_db),
|
|
58
59
|
) -> ProjectRead | None:
|
|
59
60
|
"""
|
|
@@ -94,7 +95,7 @@ async def create_project(
|
|
|
94
95
|
@router.get("/project/{project_id}/", response_model=ProjectRead)
|
|
95
96
|
async def read_project(
|
|
96
97
|
project_id: int,
|
|
97
|
-
user: UserOAuth = Depends(
|
|
98
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
98
99
|
db: AsyncSession = Depends(get_async_db),
|
|
99
100
|
) -> ProjectRead | None:
|
|
100
101
|
"""
|
|
@@ -113,7 +114,7 @@ async def read_project(
|
|
|
113
114
|
async def update_project(
|
|
114
115
|
project_id: int,
|
|
115
116
|
project_update: ProjectUpdate,
|
|
116
|
-
user: UserOAuth = Depends(
|
|
117
|
+
user: UserOAuth = Depends(get_api_user),
|
|
117
118
|
db: AsyncSession = Depends(get_async_db),
|
|
118
119
|
):
|
|
119
120
|
project = await _get_project_check_access(
|
|
@@ -140,7 +141,7 @@ async def update_project(
|
|
|
140
141
|
@router.delete("/project/{project_id}/", status_code=204)
|
|
141
142
|
async def delete_project(
|
|
142
143
|
project_id: int,
|
|
143
|
-
user: UserOAuth = Depends(
|
|
144
|
+
user: UserOAuth = Depends(get_api_user),
|
|
144
145
|
db: AsyncSession = Depends(get_async_db),
|
|
145
146
|
) -> Response:
|
|
146
147
|
"""
|
|
@@ -11,7 +11,8 @@ from fractal_server.app.db import get_async_db
|
|
|
11
11
|
from fractal_server.app.models import UserOAuth
|
|
12
12
|
from fractal_server.app.models.v2 import LinkUserProjectV2
|
|
13
13
|
from fractal_server.app.models.v2 import ProjectV2
|
|
14
|
-
from fractal_server.app.routes.auth import
|
|
14
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
15
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
15
16
|
from fractal_server.app.schemas.v2 import ProjectAccessRead
|
|
16
17
|
from fractal_server.app.schemas.v2 import ProjectGuestCreate
|
|
17
18
|
from fractal_server.app.schemas.v2 import ProjectGuestRead
|
|
@@ -33,7 +34,7 @@ router = APIRouter()
|
|
|
33
34
|
)
|
|
34
35
|
async def get_project_guests(
|
|
35
36
|
project_id: int,
|
|
36
|
-
owner: UserOAuth = Depends(
|
|
37
|
+
owner: UserOAuth = Depends(get_api_guest),
|
|
37
38
|
db: AsyncSession = Depends(get_async_db),
|
|
38
39
|
) -> list[ProjectGuestRead]:
|
|
39
40
|
"""
|
|
@@ -68,7 +69,7 @@ async def invite_guest(
|
|
|
68
69
|
project_id: int,
|
|
69
70
|
email: EmailStr,
|
|
70
71
|
project_invitation: ProjectGuestCreate,
|
|
71
|
-
owner: UserOAuth = Depends(
|
|
72
|
+
owner: UserOAuth = Depends(get_api_user),
|
|
72
73
|
db: AsyncSession = Depends(get_async_db),
|
|
73
74
|
) -> Response:
|
|
74
75
|
"""
|
|
@@ -103,7 +104,7 @@ async def patch_guest(
|
|
|
103
104
|
project_id: int,
|
|
104
105
|
email: EmailStr,
|
|
105
106
|
update: ProjectGuestUpdate,
|
|
106
|
-
owner: UserOAuth = Depends(
|
|
107
|
+
owner: UserOAuth = Depends(get_api_user),
|
|
107
108
|
db: AsyncSession = Depends(get_async_db),
|
|
108
109
|
) -> Response:
|
|
109
110
|
"""
|
|
@@ -137,7 +138,7 @@ async def patch_guest(
|
|
|
137
138
|
async def revoke_guest_access(
|
|
138
139
|
project_id: int,
|
|
139
140
|
email: EmailStr,
|
|
140
|
-
owner: UserOAuth = Depends(
|
|
141
|
+
owner: UserOAuth = Depends(get_api_user),
|
|
141
142
|
db: AsyncSession = Depends(get_async_db),
|
|
142
143
|
) -> Response:
|
|
143
144
|
"""
|
|
@@ -171,13 +172,20 @@ async def revoke_guest_access(
|
|
|
171
172
|
response_model=list[ProjectInvitationRead],
|
|
172
173
|
)
|
|
173
174
|
async def get_pending_invitations(
|
|
174
|
-
user: UserOAuth = Depends(
|
|
175
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
175
176
|
db: AsyncSession = Depends(get_async_db),
|
|
176
177
|
) -> list[ProjectInvitationRead]:
|
|
177
178
|
"""
|
|
178
179
|
See your current invitations.
|
|
179
180
|
"""
|
|
180
181
|
|
|
182
|
+
if user.is_guest:
|
|
183
|
+
# The user's attribute `is_guest` is used to identify guest accounts,
|
|
184
|
+
# i.e. accounts with read only permissions on the API.
|
|
185
|
+
# This is a different concept from a project guest, which is a regular
|
|
186
|
+
# account with which a project has been shared.
|
|
187
|
+
return []
|
|
188
|
+
|
|
181
189
|
res = await db.execute(
|
|
182
190
|
select(
|
|
183
191
|
ProjectV2.id,
|
|
@@ -225,7 +233,7 @@ async def get_pending_invitations(
|
|
|
225
233
|
)
|
|
226
234
|
async def get_access_info(
|
|
227
235
|
project_id: int,
|
|
228
|
-
user: UserOAuth = Depends(
|
|
236
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
229
237
|
db: AsyncSession = Depends(get_async_db),
|
|
230
238
|
) -> ProjectAccessRead:
|
|
231
239
|
"""
|
|
@@ -272,7 +280,7 @@ async def get_access_info(
|
|
|
272
280
|
@router.post("/project/{project_id}/access/accept/", status_code=200)
|
|
273
281
|
async def accept_project_invitation(
|
|
274
282
|
project_id: int,
|
|
275
|
-
user: UserOAuth = Depends(
|
|
283
|
+
user: UserOAuth = Depends(get_api_user),
|
|
276
284
|
db: AsyncSession = Depends(get_async_db),
|
|
277
285
|
) -> Response:
|
|
278
286
|
"""
|
|
@@ -290,7 +298,7 @@ async def accept_project_invitation(
|
|
|
290
298
|
@router.delete("/project/{project_id}/access/", status_code=204)
|
|
291
299
|
async def leave_project(
|
|
292
300
|
project_id: int,
|
|
293
|
-
user: UserOAuth = Depends(
|
|
301
|
+
user: UserOAuth = Depends(get_api_user),
|
|
294
302
|
db: AsyncSession = Depends(get_async_db),
|
|
295
303
|
) -> Response:
|
|
296
304
|
"""
|
|
@@ -11,6 +11,7 @@ from fastapi import status
|
|
|
11
11
|
from sqlmodel import select
|
|
12
12
|
from sqlmodel import update
|
|
13
13
|
|
|
14
|
+
from fractal_server import __VERSION__
|
|
14
15
|
from fractal_server.app.db import AsyncSession
|
|
15
16
|
from fractal_server.app.db import get_async_db
|
|
16
17
|
from fractal_server.app.models import Profile
|
|
@@ -20,7 +21,7 @@ from fractal_server.app.models.v2 import JobV2
|
|
|
20
21
|
from fractal_server.app.routes.api.v2._aux_functions_tasks import (
|
|
21
22
|
_get_task_read_access,
|
|
22
23
|
)
|
|
23
|
-
from fractal_server.app.routes.auth import
|
|
24
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
24
25
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
25
26
|
validate_user_profile,
|
|
26
27
|
)
|
|
@@ -59,7 +60,7 @@ async def submit_job(
|
|
|
59
60
|
job_create: JobCreate,
|
|
60
61
|
background_tasks: BackgroundTasks,
|
|
61
62
|
request: Request,
|
|
62
|
-
user: UserOAuth = Depends(
|
|
63
|
+
user: UserOAuth = Depends(get_api_user),
|
|
63
64
|
db: AsyncSession = Depends(get_async_db),
|
|
64
65
|
) -> JobRead | None:
|
|
65
66
|
# Remove non-submitted Jobs from the app state when the list grows
|
|
@@ -216,11 +217,12 @@ async def submit_job(
|
|
|
216
217
|
dataset.model_dump_json(exclude={"images", "history"})
|
|
217
218
|
),
|
|
218
219
|
workflow_dump=json.loads(
|
|
219
|
-
workflow.model_dump_json(exclude={"task_list"})
|
|
220
|
+
workflow.model_dump_json(exclude={"task_list", "description"})
|
|
220
221
|
),
|
|
221
222
|
project_dump=json.loads(
|
|
222
223
|
project.model_dump_json(exclude={"resource_id"})
|
|
223
224
|
),
|
|
225
|
+
fractal_server_version=__VERSION__,
|
|
224
226
|
**job_create.model_dump(),
|
|
225
227
|
)
|
|
226
228
|
|
|
@@ -24,7 +24,8 @@ from fractal_server.app.models import LinkUserGroup
|
|
|
24
24
|
from fractal_server.app.models import UserOAuth
|
|
25
25
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
26
26
|
from fractal_server.app.models.v2 import TaskV2
|
|
27
|
-
from fractal_server.app.routes.auth import
|
|
27
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
28
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
28
29
|
from fractal_server.app.schemas.v2 import TaskCreate
|
|
29
30
|
from fractal_server.app.schemas.v2 import TaskGroupOriginEnum
|
|
30
31
|
from fractal_server.app.schemas.v2 import TaskRead
|
|
@@ -43,7 +44,7 @@ async def get_list_task(
|
|
|
43
44
|
category: str | None = None,
|
|
44
45
|
modality: str | None = None,
|
|
45
46
|
author: str | None = None,
|
|
46
|
-
user: UserOAuth = Depends(
|
|
47
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
47
48
|
db: AsyncSession = Depends(get_async_db),
|
|
48
49
|
) -> list[TaskRead]:
|
|
49
50
|
"""
|
|
@@ -88,7 +89,7 @@ async def get_list_task(
|
|
|
88
89
|
@router.get("/{task_id}/", response_model=TaskRead)
|
|
89
90
|
async def get_task(
|
|
90
91
|
task_id: int,
|
|
91
|
-
user: UserOAuth = Depends(
|
|
92
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
92
93
|
db: AsyncSession = Depends(get_async_db),
|
|
93
94
|
) -> TaskRead:
|
|
94
95
|
"""
|
|
@@ -102,7 +103,7 @@ async def get_task(
|
|
|
102
103
|
async def patch_task(
|
|
103
104
|
task_id: int,
|
|
104
105
|
task_update: TaskUpdate,
|
|
105
|
-
user: UserOAuth = Depends(
|
|
106
|
+
user: UserOAuth = Depends(get_api_user),
|
|
106
107
|
db: AsyncSession = Depends(get_async_db),
|
|
107
108
|
) -> TaskRead | None:
|
|
108
109
|
"""
|
|
@@ -140,7 +141,7 @@ async def create_task(
|
|
|
140
141
|
task: TaskCreate,
|
|
141
142
|
user_group_id: int | None = None,
|
|
142
143
|
private: bool = False,
|
|
143
|
-
user: UserOAuth = Depends(
|
|
144
|
+
user: UserOAuth = Depends(get_api_user),
|
|
144
145
|
db: AsyncSession = Depends(get_async_db),
|
|
145
146
|
) -> TaskRead | None:
|
|
146
147
|
"""
|
|
@@ -221,7 +222,7 @@ async def create_task(
|
|
|
221
222
|
@router.delete("/{task_id}/", status_code=204)
|
|
222
223
|
async def delete_task(
|
|
223
224
|
task_id: int,
|
|
224
|
-
user: UserOAuth = Depends(
|
|
225
|
+
user: UserOAuth = Depends(get_api_user),
|
|
225
226
|
db: AsyncSession = Depends(get_async_db),
|
|
226
227
|
) -> Response:
|
|
227
228
|
"""
|
|
@@ -14,12 +14,13 @@ from pydantic import BaseModel
|
|
|
14
14
|
from pydantic import ValidationError
|
|
15
15
|
from pydantic import model_validator
|
|
16
16
|
|
|
17
|
+
from fractal_server import __VERSION__
|
|
17
18
|
from fractal_server.app.db import AsyncSession
|
|
18
19
|
from fractal_server.app.db import get_async_db
|
|
19
20
|
from fractal_server.app.models import UserOAuth
|
|
20
21
|
from fractal_server.app.models.v2 import TaskGroupActivityV2
|
|
21
22
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
22
|
-
from fractal_server.app.routes.auth import
|
|
23
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
23
24
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
24
25
|
validate_user_profile,
|
|
25
26
|
)
|
|
@@ -158,7 +159,7 @@ async def collect_tasks_pip(
|
|
|
158
159
|
request_data: CollectionRequestData = Depends(parse_request_data),
|
|
159
160
|
private: bool = False,
|
|
160
161
|
user_group_id: int | None = None,
|
|
161
|
-
user: UserOAuth = Depends(
|
|
162
|
+
user: UserOAuth = Depends(get_api_user),
|
|
162
163
|
db: AsyncSession = Depends(get_async_db),
|
|
163
164
|
) -> TaskGroupActivityRead:
|
|
164
165
|
"""
|
|
@@ -332,6 +333,7 @@ async def collect_tasks_pip(
|
|
|
332
333
|
action=TaskGroupActivityAction.COLLECT,
|
|
333
334
|
pkg_name=task_group.pkg_name,
|
|
334
335
|
version=task_group.version,
|
|
336
|
+
fractal_server_version=__VERSION__,
|
|
335
337
|
)
|
|
336
338
|
db.add(task_group_activity)
|
|
337
339
|
await db.commit()
|
|
@@ -12,7 +12,7 @@ from sqlalchemy.ext.asyncio import AsyncSession
|
|
|
12
12
|
from fractal_server.app.db import get_async_db
|
|
13
13
|
from fractal_server.app.models import UserOAuth
|
|
14
14
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
15
|
-
from fractal_server.app.routes.auth import
|
|
15
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
16
16
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
17
17
|
validate_user_profile,
|
|
18
18
|
)
|
|
@@ -43,7 +43,7 @@ async def collect_task_custom(
|
|
|
43
43
|
task_collect: TaskCollectCustom,
|
|
44
44
|
private: bool = False,
|
|
45
45
|
user_group_id: int | None = None,
|
|
46
|
-
user: UserOAuth = Depends(
|
|
46
|
+
user: UserOAuth = Depends(get_api_user),
|
|
47
47
|
db: AsyncSession = Depends(get_async_db),
|
|
48
48
|
) -> list[TaskRead]:
|
|
49
49
|
# Get validated resource and profile
|
|
@@ -10,6 +10,7 @@ from fastapi import Response
|
|
|
10
10
|
from fastapi import UploadFile
|
|
11
11
|
from fastapi import status
|
|
12
12
|
|
|
13
|
+
from fractal_server import __VERSION__
|
|
13
14
|
from fractal_server.app.db import AsyncSession
|
|
14
15
|
from fractal_server.app.db import get_async_db
|
|
15
16
|
from fractal_server.app.models import UserOAuth
|
|
@@ -27,7 +28,7 @@ from fractal_server.app.routes.api.v2._aux_functions_tasks import (
|
|
|
27
28
|
from fractal_server.app.routes.api.v2._aux_functions_tasks import (
|
|
28
29
|
_verify_non_duplication_user_constraint,
|
|
29
30
|
)
|
|
30
|
-
from fractal_server.app.routes.auth import
|
|
31
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
31
32
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
32
33
|
validate_user_profile,
|
|
33
34
|
)
|
|
@@ -83,7 +84,7 @@ async def collect_task_pixi(
|
|
|
83
84
|
pixi_version: NonEmptyStr | None = Form(None),
|
|
84
85
|
private: bool = False,
|
|
85
86
|
user_group_id: int | None = None,
|
|
86
|
-
user: UserOAuth = Depends(
|
|
87
|
+
user: UserOAuth = Depends(get_api_user),
|
|
87
88
|
db: AsyncSession = Depends(get_async_db),
|
|
88
89
|
) -> TaskGroupActivityRead:
|
|
89
90
|
# Get validated resource and profile
|
|
@@ -182,6 +183,7 @@ async def collect_task_pixi(
|
|
|
182
183
|
action=TaskGroupActivityAction.COLLECT,
|
|
183
184
|
pkg_name=task_group.pkg_name,
|
|
184
185
|
version=task_group.version,
|
|
186
|
+
fractal_server_version=__VERSION__,
|
|
185
187
|
)
|
|
186
188
|
db.add(task_group_activity)
|
|
187
189
|
await db.commit()
|
|
@@ -4,9 +4,6 @@ from fastapi import APIRouter
|
|
|
4
4
|
from fastapi import Depends
|
|
5
5
|
from fastapi import HTTPException
|
|
6
6
|
from fastapi import status
|
|
7
|
-
from packaging.version import InvalidVersion
|
|
8
|
-
from packaging.version import Version
|
|
9
|
-
from packaging.version import parse
|
|
10
7
|
from pydantic.types import AwareDatetime
|
|
11
8
|
from sqlmodel import or_
|
|
12
9
|
from sqlmodel import select
|
|
@@ -17,13 +14,15 @@ from fractal_server.app.models import LinkUserGroup
|
|
|
17
14
|
from fractal_server.app.models import UserOAuth
|
|
18
15
|
from fractal_server.app.models.v2 import TaskGroupActivityV2
|
|
19
16
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
20
|
-
from fractal_server.app.routes.auth import
|
|
17
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
18
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
21
19
|
from fractal_server.app.routes.auth._aux_auth import (
|
|
22
20
|
_get_default_usergroup_id_or_none,
|
|
23
21
|
)
|
|
24
22
|
from fractal_server.app.routes.auth._aux_auth import (
|
|
25
23
|
_verify_user_belongs_to_group,
|
|
26
24
|
)
|
|
25
|
+
from fractal_server.app.routes.aux._versions import _version_sort_key
|
|
27
26
|
from fractal_server.app.schemas.v2 import TaskGroupActivityAction
|
|
28
27
|
from fractal_server.app.schemas.v2 import TaskGroupActivityRead
|
|
29
28
|
from fractal_server.app.schemas.v2 import TaskGroupActivityStatus
|
|
@@ -42,26 +41,6 @@ router = APIRouter()
|
|
|
42
41
|
logger = set_logger(__name__)
|
|
43
42
|
|
|
44
43
|
|
|
45
|
-
def _version_sort_key(
|
|
46
|
-
task_group: TaskGroupV2,
|
|
47
|
-
) -> tuple[int, Version | str | None]:
|
|
48
|
-
"""
|
|
49
|
-
Returns a tuple used as (reverse) ordering key for TaskGroups in
|
|
50
|
-
`get_task_group_list`.
|
|
51
|
-
The TaskGroups with a parsable versions are the first in order,
|
|
52
|
-
sorted according to the sorting rules of packaging.version.Version.
|
|
53
|
-
Next in order we have the TaskGroups with non-null non-parsable versions,
|
|
54
|
-
sorted alphabetically.
|
|
55
|
-
Last we have the TaskGroups with null version.
|
|
56
|
-
"""
|
|
57
|
-
if task_group.version is None:
|
|
58
|
-
return (0, task_group.version)
|
|
59
|
-
try:
|
|
60
|
-
return (2, parse(task_group.version))
|
|
61
|
-
except InvalidVersion:
|
|
62
|
-
return (1, task_group.version)
|
|
63
|
-
|
|
64
|
-
|
|
65
44
|
@router.get("/activity/", response_model=list[TaskGroupActivityRead])
|
|
66
45
|
async def get_task_group_activity_list(
|
|
67
46
|
task_group_activity_id: int | None = None,
|
|
@@ -70,7 +49,7 @@ async def get_task_group_activity_list(
|
|
|
70
49
|
status: TaskGroupActivityStatus | None = None,
|
|
71
50
|
action: TaskGroupActivityAction | None = None,
|
|
72
51
|
timestamp_started_min: AwareDatetime | None = None,
|
|
73
|
-
user: UserOAuth = Depends(
|
|
52
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
74
53
|
db: AsyncSession = Depends(get_async_db),
|
|
75
54
|
) -> list[TaskGroupActivityRead]:
|
|
76
55
|
stm = select(TaskGroupActivityV2).where(
|
|
@@ -102,7 +81,7 @@ async def get_task_group_activity_list(
|
|
|
102
81
|
)
|
|
103
82
|
async def get_task_group_activity(
|
|
104
83
|
task_group_activity_id: int,
|
|
105
|
-
user: UserOAuth = Depends(
|
|
84
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
106
85
|
db: AsyncSession = Depends(get_async_db),
|
|
107
86
|
) -> TaskGroupActivityRead:
|
|
108
87
|
activity = await db.get(TaskGroupActivityV2, task_group_activity_id)
|
|
@@ -126,7 +105,7 @@ async def get_task_group_activity(
|
|
|
126
105
|
|
|
127
106
|
@router.get("/", response_model=list[tuple[str, list[TaskGroupRead]]])
|
|
128
107
|
async def get_task_group_list(
|
|
129
|
-
user: UserOAuth = Depends(
|
|
108
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
130
109
|
db: AsyncSession = Depends(get_async_db),
|
|
131
110
|
only_active: bool = False,
|
|
132
111
|
only_owner: bool = False,
|
|
@@ -175,7 +154,7 @@ async def get_task_group_list(
|
|
|
175
154
|
await remove_duplicate_task_groups(
|
|
176
155
|
task_groups=sorted(
|
|
177
156
|
list(groups),
|
|
178
|
-
key=_version_sort_key,
|
|
157
|
+
key=lambda group: _version_sort_key(group.version),
|
|
179
158
|
reverse=True,
|
|
180
159
|
),
|
|
181
160
|
user_id=user.id,
|
|
@@ -194,7 +173,7 @@ async def get_task_group_list(
|
|
|
194
173
|
@router.get("/{task_group_id}/", response_model=TaskGroupRead)
|
|
195
174
|
async def get_task_group(
|
|
196
175
|
task_group_id: int,
|
|
197
|
-
user: UserOAuth = Depends(
|
|
176
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
198
177
|
db: AsyncSession = Depends(get_async_db),
|
|
199
178
|
) -> TaskGroupRead:
|
|
200
179
|
"""
|
|
@@ -212,7 +191,7 @@ async def get_task_group(
|
|
|
212
191
|
async def patch_task_group(
|
|
213
192
|
task_group_id: int,
|
|
214
193
|
task_group_update: TaskGroupUpdate,
|
|
215
|
-
user: UserOAuth = Depends(
|
|
194
|
+
user: UserOAuth = Depends(get_api_user),
|
|
216
195
|
db: AsyncSession = Depends(get_async_db),
|
|
217
196
|
) -> TaskGroupRead:
|
|
218
197
|
"""
|
|
@@ -5,11 +5,12 @@ from fastapi import HTTPException
|
|
|
5
5
|
from fastapi import Response
|
|
6
6
|
from fastapi import status
|
|
7
7
|
|
|
8
|
+
from fractal_server import __VERSION__
|
|
8
9
|
from fractal_server.app.db import AsyncSession
|
|
9
10
|
from fractal_server.app.db import get_async_db
|
|
10
11
|
from fractal_server.app.models import UserOAuth
|
|
11
12
|
from fractal_server.app.models.v2 import TaskGroupActivityV2
|
|
12
|
-
from fractal_server.app.routes.auth import
|
|
13
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
13
14
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
14
15
|
validate_user_profile,
|
|
15
16
|
)
|
|
@@ -51,7 +52,7 @@ async def deactivate_task_group(
|
|
|
51
52
|
task_group_id: int,
|
|
52
53
|
background_tasks: BackgroundTasks,
|
|
53
54
|
response: Response,
|
|
54
|
-
user: UserOAuth = Depends(
|
|
55
|
+
user: UserOAuth = Depends(get_api_user),
|
|
55
56
|
db: AsyncSession = Depends(get_async_db),
|
|
56
57
|
) -> TaskGroupActivityRead:
|
|
57
58
|
"""
|
|
@@ -99,6 +100,7 @@ async def deactivate_task_group(
|
|
|
99
100
|
),
|
|
100
101
|
timestamp_started=get_timestamp(),
|
|
101
102
|
timestamp_ended=get_timestamp(),
|
|
103
|
+
fractal_server_version=__VERSION__,
|
|
102
104
|
)
|
|
103
105
|
db.add(task_group)
|
|
104
106
|
db.add(task_group_activity)
|
|
@@ -114,6 +116,7 @@ async def deactivate_task_group(
|
|
|
114
116
|
pkg_name=task_group.pkg_name,
|
|
115
117
|
version=task_group.version,
|
|
116
118
|
timestamp_started=get_timestamp(),
|
|
119
|
+
fractal_server_version=__VERSION__,
|
|
117
120
|
)
|
|
118
121
|
task_group.active = False
|
|
119
122
|
db.add(task_group)
|
|
@@ -155,7 +158,7 @@ async def reactivate_task_group(
|
|
|
155
158
|
task_group_id: int,
|
|
156
159
|
background_tasks: BackgroundTasks,
|
|
157
160
|
response: Response,
|
|
158
|
-
user: UserOAuth = Depends(
|
|
161
|
+
user: UserOAuth = Depends(get_api_user),
|
|
159
162
|
db: AsyncSession = Depends(get_async_db),
|
|
160
163
|
) -> TaskGroupRead:
|
|
161
164
|
"""
|
|
@@ -202,6 +205,7 @@ async def reactivate_task_group(
|
|
|
202
205
|
),
|
|
203
206
|
timestamp_started=get_timestamp(),
|
|
204
207
|
timestamp_ended=get_timestamp(),
|
|
208
|
+
fractal_server_version=__VERSION__,
|
|
205
209
|
)
|
|
206
210
|
db.add(task_group)
|
|
207
211
|
db.add(task_group_activity)
|
|
@@ -225,6 +229,7 @@ async def reactivate_task_group(
|
|
|
225
229
|
pkg_name=task_group.pkg_name,
|
|
226
230
|
version=task_group.version,
|
|
227
231
|
timestamp_started=get_timestamp(),
|
|
232
|
+
fractal_server_version=__VERSION__,
|
|
228
233
|
)
|
|
229
234
|
db.add(task_group_activity)
|
|
230
235
|
await db.commit()
|
|
@@ -263,7 +268,7 @@ async def delete_task_group(
|
|
|
263
268
|
task_group_id: int,
|
|
264
269
|
background_tasks: BackgroundTasks,
|
|
265
270
|
response: Response,
|
|
266
|
-
user: UserOAuth = Depends(
|
|
271
|
+
user: UserOAuth = Depends(get_api_user),
|
|
267
272
|
db: AsyncSession = Depends(get_async_db),
|
|
268
273
|
) -> TaskGroupActivityRead:
|
|
269
274
|
"""
|
|
@@ -288,6 +293,7 @@ async def delete_task_group(
|
|
|
288
293
|
pkg_name=task_group.pkg_name,
|
|
289
294
|
version=(task_group.version or "N/A"),
|
|
290
295
|
timestamp_started=get_timestamp(),
|
|
296
|
+
fractal_server_version=__VERSION__,
|
|
291
297
|
)
|
|
292
298
|
db.add(task_group_activity)
|
|
293
299
|
await db.commit()
|
|
@@ -17,7 +17,8 @@ from fractal_server.app.models import LinkUserGroup
|
|
|
17
17
|
from fractal_server.app.models import UserOAuth
|
|
18
18
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
19
19
|
from fractal_server.app.models.v2 import TaskV2
|
|
20
|
-
from fractal_server.app.routes.auth import
|
|
20
|
+
from fractal_server.app.routes.auth import get_api_guest
|
|
21
|
+
from fractal_server.app.routes.auth import get_api_user
|
|
21
22
|
from fractal_server.app.schemas.v2 import TaskType
|
|
22
23
|
from fractal_server.app.schemas.v2 import WorkflowTaskRead
|
|
23
24
|
from fractal_server.app.schemas.v2 import WorkflowTaskReplace
|
|
@@ -77,7 +78,7 @@ class TaskVersionRead(BaseModel):
|
|
|
77
78
|
async def get_workflow_version_update_candidates(
|
|
78
79
|
project_id: int,
|
|
79
80
|
workflow_id: int,
|
|
80
|
-
user: UserOAuth = Depends(
|
|
81
|
+
user: UserOAuth = Depends(get_api_guest),
|
|
81
82
|
db: AsyncSession = Depends(get_async_db),
|
|
82
83
|
) -> list[list[TaskVersionRead]]:
|
|
83
84
|
workflow = await _get_workflow_check_access(
|
|
@@ -180,7 +181,7 @@ async def replace_workflowtask(
|
|
|
180
181
|
workflow_task_id: int,
|
|
181
182
|
task_id: int,
|
|
182
183
|
replace: WorkflowTaskReplace,
|
|
183
|
-
user: UserOAuth = Depends(
|
|
184
|
+
user: UserOAuth = Depends(get_api_user),
|
|
184
185
|
db: AsyncSession = Depends(get_async_db),
|
|
185
186
|
) -> WorkflowTaskRead:
|
|
186
187
|
# Get objects from database
|