fractal-server 2.17.0a3__py3-none-any.whl → 2.17.0a5__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/__main__.py +137 -120
- fractal_server/app/models/security.py +19 -21
- fractal_server/app/models/user_settings.py +1 -0
- fractal_server/app/models/v2/task_group.py +1 -0
- fractal_server/app/routes/admin/v2/accounting.py +3 -3
- fractal_server/app/routes/admin/v2/impersonate.py +2 -2
- fractal_server/app/routes/admin/v2/job.py +6 -6
- fractal_server/app/routes/admin/v2/profile.py +4 -4
- fractal_server/app/routes/admin/v2/project.py +2 -2
- fractal_server/app/routes/admin/v2/resource.py +42 -8
- fractal_server/app/routes/admin/v2/task.py +2 -2
- fractal_server/app/routes/admin/v2/task_group.py +5 -5
- fractal_server/app/routes/admin/v2/task_group_lifecycle.py +4 -4
- fractal_server/app/routes/api/__init__.py +5 -5
- fractal_server/app/routes/api/v2/dataset.py +10 -19
- fractal_server/app/routes/api/v2/history.py +8 -8
- fractal_server/app/routes/api/v2/images.py +5 -5
- fractal_server/app/routes/api/v2/job.py +8 -8
- fractal_server/app/routes/api/v2/pre_submission_checks.py +3 -3
- fractal_server/app/routes/api/v2/project.py +6 -6
- fractal_server/app/routes/api/v2/status_legacy.py +2 -2
- fractal_server/app/routes/api/v2/submit.py +24 -26
- fractal_server/app/routes/api/v2/task.py +6 -7
- fractal_server/app/routes/api/v2/task_collection.py +4 -3
- fractal_server/app/routes/api/v2/task_collection_custom.py +4 -3
- fractal_server/app/routes/api/v2/task_collection_pixi.py +2 -2
- fractal_server/app/routes/api/v2/task_group.py +6 -6
- fractal_server/app/routes/api/v2/task_group_lifecycle.py +4 -4
- fractal_server/app/routes/api/v2/task_version_update.py +3 -3
- fractal_server/app/routes/api/v2/workflow.py +9 -9
- fractal_server/app/routes/api/v2/workflow_import.py +2 -2
- fractal_server/app/routes/api/v2/workflowtask.py +5 -5
- fractal_server/app/routes/auth/__init__.py +34 -5
- fractal_server/app/routes/auth/current_user.py +22 -67
- fractal_server/app/routes/auth/group.py +8 -35
- fractal_server/app/routes/auth/register.py +2 -2
- fractal_server/app/routes/auth/users.py +5 -46
- fractal_server/app/schemas/__init__.py +0 -1
- fractal_server/app/schemas/user.py +23 -0
- fractal_server/app/schemas/v2/task_group.py +1 -0
- fractal_server/app/security/__init__.py +134 -46
- fractal_server/app/security/signup_email.py +52 -34
- fractal_server/config/__init__.py +1 -7
- fractal_server/config/_email.py +10 -47
- fractal_server/config/_main.py +14 -3
- fractal_server/migrations/versions/f65ee53991e3_user_settings_related.py +67 -0
- fractal_server/runner/config/_slurm.py +3 -2
- fractal_server/runner/executors/slurm_common/base_slurm_runner.py +2 -2
- fractal_server/runner/executors/slurm_common/get_slurm_config.py +1 -1
- fractal_server/runner/executors/slurm_common/slurm_config.py +7 -13
- fractal_server/runner/executors/slurm_ssh/runner.py +1 -1
- fractal_server/runner/executors/slurm_sudo/runner.py +1 -1
- fractal_server/runner/v2/_slurm_ssh.py +2 -1
- fractal_server/runner/v2/_slurm_sudo.py +1 -1
- fractal_server/runner/v2/submit_workflow.py +12 -12
- {fractal_server-2.17.0a3.dist-info → fractal_server-2.17.0a5.dist-info}/METADATA +1 -2
- {fractal_server-2.17.0a3.dist-info → fractal_server-2.17.0a5.dist-info}/RECORD +61 -64
- fractal_server/app/routes/aux/validate_user_settings.py +0 -76
- fractal_server/app/schemas/user_settings.py +0 -63
- fractal_server/app/user_settings.py +0 -32
- fractal_server/config/_init_data.py +0 -27
- {fractal_server-2.17.0a3.dist-info → fractal_server-2.17.0a5.dist-info}/WHEEL +0 -0
- {fractal_server-2.17.0a3.dist-info → fractal_server-2.17.0a5.dist-info}/entry_points.txt +0 -0
- {fractal_server-2.17.0a3.dist-info → fractal_server-2.17.0a5.dist-info}/licenses/LICENSE +0 -0
|
@@ -17,16 +17,14 @@ from ._aux_functions import clean_app_job_list_v2
|
|
|
17
17
|
from ._aux_functions_tasks import _check_type_filters_compatibility
|
|
18
18
|
from fractal_server.app.db import AsyncSession
|
|
19
19
|
from fractal_server.app.db import get_async_db
|
|
20
|
+
from fractal_server.app.models import Profile
|
|
20
21
|
from fractal_server.app.models import TaskGroupV2
|
|
21
22
|
from fractal_server.app.models import UserOAuth
|
|
22
23
|
from fractal_server.app.models.v2 import JobV2
|
|
23
24
|
from fractal_server.app.routes.api.v2._aux_functions_tasks import (
|
|
24
25
|
_get_task_read_access,
|
|
25
26
|
)
|
|
26
|
-
from fractal_server.app.routes.auth import
|
|
27
|
-
from fractal_server.app.routes.aux.validate_user_settings import (
|
|
28
|
-
validate_user_settings,
|
|
29
|
-
)
|
|
27
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
30
28
|
from fractal_server.app.schemas.v2 import JobCreateV2
|
|
31
29
|
from fractal_server.app.schemas.v2 import JobReadV2
|
|
32
30
|
from fractal_server.app.schemas.v2 import JobStatusTypeV2
|
|
@@ -39,7 +37,7 @@ from fractal_server.runner.set_start_and_last_task_index import (
|
|
|
39
37
|
from fractal_server.runner.v2.submit_workflow import submit_workflow
|
|
40
38
|
from fractal_server.syringe import Inject
|
|
41
39
|
|
|
42
|
-
|
|
40
|
+
FRACTAL_CACHE_DIR = ".fractal_cache"
|
|
43
41
|
router = APIRouter()
|
|
44
42
|
logger = set_logger(__name__)
|
|
45
43
|
|
|
@@ -56,7 +54,7 @@ async def apply_workflow(
|
|
|
56
54
|
job_create: JobCreateV2,
|
|
57
55
|
background_tasks: BackgroundTasks,
|
|
58
56
|
request: Request,
|
|
59
|
-
user: UserOAuth = Depends(
|
|
57
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
60
58
|
db: AsyncSession = Depends(get_async_db),
|
|
61
59
|
) -> JobReadV2 | None:
|
|
62
60
|
# Remove non-submitted V2 jobs from the app state when the list grows
|
|
@@ -80,6 +78,17 @@ async def apply_workflow(
|
|
|
80
78
|
project = output["project"]
|
|
81
79
|
dataset = output["dataset"]
|
|
82
80
|
|
|
81
|
+
# Verify that user's resource matches with project resource
|
|
82
|
+
res = await db.execute(
|
|
83
|
+
select(Profile.resource_id).where(Profile.id == user.profile_id)
|
|
84
|
+
)
|
|
85
|
+
user_resource_id = res.scalar_one()
|
|
86
|
+
if project.resource_id != user_resource_id:
|
|
87
|
+
raise HTTPException(
|
|
88
|
+
status_code=status.HTTP_422_UNPROCESSABLE_CONTENT,
|
|
89
|
+
detail="Project resource does not match with user's resource",
|
|
90
|
+
)
|
|
91
|
+
|
|
83
92
|
workflow = await _get_workflow_check_owner(
|
|
84
93
|
project_id=project_id, workflow_id=workflow_id, user_id=user.id, db=db
|
|
85
94
|
)
|
|
@@ -129,10 +138,7 @@ async def apply_workflow(
|
|
|
129
138
|
user=user,
|
|
130
139
|
db=db,
|
|
131
140
|
)
|
|
132
|
-
|
|
133
|
-
user_settings = await validate_user_settings(
|
|
134
|
-
user=user, backend=resource.type, db=db
|
|
135
|
-
)
|
|
141
|
+
|
|
136
142
|
# Check that no other job with the same dataset_id is SUBMITTED
|
|
137
143
|
stm = (
|
|
138
144
|
select(JobV2)
|
|
@@ -150,7 +156,7 @@ async def apply_workflow(
|
|
|
150
156
|
)
|
|
151
157
|
|
|
152
158
|
if job_create.slurm_account is not None:
|
|
153
|
-
if job_create.slurm_account not in
|
|
159
|
+
if job_create.slurm_account not in user.slurm_accounts:
|
|
154
160
|
raise HTTPException(
|
|
155
161
|
status_code=status.HTTP_422_UNPROCESSABLE_CONTENT,
|
|
156
162
|
detail=(
|
|
@@ -159,8 +165,8 @@ async def apply_workflow(
|
|
|
159
165
|
),
|
|
160
166
|
)
|
|
161
167
|
else:
|
|
162
|
-
if len(
|
|
163
|
-
job_create.slurm_account =
|
|
168
|
+
if len(user.slurm_accounts) > 0:
|
|
169
|
+
job_create.slurm_account = user.slurm_accounts[0]
|
|
164
170
|
|
|
165
171
|
# User appropriate FractalSSH object
|
|
166
172
|
if resource.type == ResourceType.SLURM_SSH:
|
|
@@ -226,22 +232,17 @@ async def apply_workflow(
|
|
|
226
232
|
)
|
|
227
233
|
|
|
228
234
|
# Define user-side job directory
|
|
235
|
+
cache_dir = Path(user.project_dir, FRACTAL_CACHE_DIR)
|
|
229
236
|
match resource.type:
|
|
230
237
|
case ResourceType.LOCAL:
|
|
231
238
|
WORKFLOW_DIR_REMOTE = WORKFLOW_DIR_LOCAL
|
|
232
|
-
cache_dir = None
|
|
233
239
|
case ResourceType.SLURM_SUDO:
|
|
234
|
-
cache_dir = (
|
|
235
|
-
Path(user_settings.project_dir) / ".fractal_cache"
|
|
236
|
-
if user_settings.project_dir is not None
|
|
237
|
-
else None
|
|
238
|
-
)
|
|
239
240
|
WORKFLOW_DIR_REMOTE = cache_dir / WORKFLOW_DIR_LOCAL.name
|
|
240
241
|
case ResourceType.SLURM_SSH:
|
|
241
|
-
WORKFLOW_DIR_REMOTE = (
|
|
242
|
-
|
|
242
|
+
WORKFLOW_DIR_REMOTE = Path(
|
|
243
|
+
profile.jobs_remote_dir,
|
|
244
|
+
WORKFLOW_DIR_LOCAL.name,
|
|
243
245
|
)
|
|
244
|
-
cache_dir = None
|
|
245
246
|
|
|
246
247
|
# Update job folders in the db
|
|
247
248
|
job.working_dir = WORKFLOW_DIR_LOCAL.as_posix()
|
|
@@ -249,9 +250,6 @@ async def apply_workflow(
|
|
|
249
250
|
await db.merge(job)
|
|
250
251
|
await db.commit()
|
|
251
252
|
|
|
252
|
-
# Expunge user settings from db, to use in background task
|
|
253
|
-
db.expunge(user_settings)
|
|
254
|
-
|
|
255
253
|
background_tasks.add_task(
|
|
256
254
|
submit_workflow,
|
|
257
255
|
workflow_id=workflow.id,
|
|
@@ -259,7 +257,7 @@ async def apply_workflow(
|
|
|
259
257
|
job_id=job.id,
|
|
260
258
|
user_id=user.id,
|
|
261
259
|
worker_init=job.worker_init,
|
|
262
|
-
user_cache_dir=cache_dir.as_posix()
|
|
260
|
+
user_cache_dir=cache_dir.as_posix(),
|
|
263
261
|
fractal_ssh=fractal_ssh,
|
|
264
262
|
resource=resource,
|
|
265
263
|
profile=profile,
|
|
@@ -21,8 +21,7 @@ from fractal_server.app.models import LinkUserGroup
|
|
|
21
21
|
from fractal_server.app.models import UserOAuth
|
|
22
22
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
23
23
|
from fractal_server.app.models.v2 import TaskV2
|
|
24
|
-
from fractal_server.app.routes.auth import
|
|
25
|
-
from fractal_server.app.routes.auth import current_active_verified_user
|
|
24
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
26
25
|
from fractal_server.app.schemas.v2 import TaskCreateV2
|
|
27
26
|
from fractal_server.app.schemas.v2 import TaskGroupV2OriginEnum
|
|
28
27
|
from fractal_server.app.schemas.v2 import TaskReadV2
|
|
@@ -41,7 +40,7 @@ async def get_list_task(
|
|
|
41
40
|
category: str | None = None,
|
|
42
41
|
modality: str | None = None,
|
|
43
42
|
author: str | None = None,
|
|
44
|
-
user: UserOAuth = Depends(
|
|
43
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
45
44
|
db: AsyncSession = Depends(get_async_db),
|
|
46
45
|
) -> list[TaskReadV2]:
|
|
47
46
|
"""
|
|
@@ -83,7 +82,7 @@ async def get_list_task(
|
|
|
83
82
|
@router.get("/{task_id}/", response_model=TaskReadV2)
|
|
84
83
|
async def get_task(
|
|
85
84
|
task_id: int,
|
|
86
|
-
user: UserOAuth = Depends(
|
|
85
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
87
86
|
db: AsyncSession = Depends(get_async_db),
|
|
88
87
|
) -> TaskReadV2:
|
|
89
88
|
"""
|
|
@@ -97,7 +96,7 @@ async def get_task(
|
|
|
97
96
|
async def patch_task(
|
|
98
97
|
task_id: int,
|
|
99
98
|
task_update: TaskUpdateV2,
|
|
100
|
-
user: UserOAuth = Depends(
|
|
99
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
101
100
|
db: AsyncSession = Depends(get_async_db),
|
|
102
101
|
) -> TaskReadV2 | None:
|
|
103
102
|
"""
|
|
@@ -138,7 +137,7 @@ async def create_task(
|
|
|
138
137
|
task: TaskCreateV2,
|
|
139
138
|
user_group_id: int | None = None,
|
|
140
139
|
private: bool = False,
|
|
141
|
-
user: UserOAuth = Depends(
|
|
140
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
142
141
|
db: AsyncSession = Depends(get_async_db),
|
|
143
142
|
) -> TaskReadV2 | None:
|
|
144
143
|
"""
|
|
@@ -212,7 +211,7 @@ async def create_task(
|
|
|
212
211
|
@router.delete("/{task_id}/", status_code=204)
|
|
213
212
|
async def delete_task(
|
|
214
213
|
task_id: int,
|
|
215
|
-
user: UserOAuth = Depends(
|
|
214
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
216
215
|
db: AsyncSession = Depends(get_async_db),
|
|
217
216
|
) -> Response:
|
|
218
217
|
"""
|
|
@@ -33,7 +33,7 @@ from ._aux_functions_tasks import _verify_non_duplication_group_path
|
|
|
33
33
|
from ._aux_functions_tasks import _verify_non_duplication_user_constraint
|
|
34
34
|
from fractal_server.app.models import UserOAuth
|
|
35
35
|
from fractal_server.app.models.v2 import TaskGroupActivityV2
|
|
36
|
-
from fractal_server.app.routes.auth import
|
|
36
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
37
37
|
from fractal_server.app.schemas.v2 import ResourceType
|
|
38
38
|
from fractal_server.app.schemas.v2 import (
|
|
39
39
|
TaskGroupActivityActionV2,
|
|
@@ -161,7 +161,7 @@ async def collect_tasks_pip(
|
|
|
161
161
|
request_data: CollectionRequestData = Depends(parse_request_data),
|
|
162
162
|
private: bool = False,
|
|
163
163
|
user_group_id: int | None = None,
|
|
164
|
-
user: UserOAuth = Depends(
|
|
164
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
165
165
|
db: AsyncSession = Depends(get_async_db),
|
|
166
166
|
) -> TaskGroupActivityV2Read:
|
|
167
167
|
"""
|
|
@@ -183,6 +183,7 @@ async def collect_tasks_pip(
|
|
|
183
183
|
# Initialize task-group attributes
|
|
184
184
|
task_group_attrs = dict(
|
|
185
185
|
user_id=user.id,
|
|
186
|
+
resource_id=resource_id,
|
|
186
187
|
origin=request_data.origin,
|
|
187
188
|
)
|
|
188
189
|
|
|
@@ -320,7 +321,7 @@ async def collect_tasks_pip(
|
|
|
320
321
|
)
|
|
321
322
|
|
|
322
323
|
# Create TaskGroupV2 object
|
|
323
|
-
task_group = TaskGroupV2(**task_group_attrs
|
|
324
|
+
task_group = TaskGroupV2(**task_group_attrs)
|
|
324
325
|
db.add(task_group)
|
|
325
326
|
await db.commit()
|
|
326
327
|
await db.refresh(task_group)
|
|
@@ -17,7 +17,7 @@ from ._aux_functions_tasks import _verify_non_duplication_user_constraint
|
|
|
17
17
|
from fractal_server.app.db import get_async_db
|
|
18
18
|
from fractal_server.app.models import UserOAuth
|
|
19
19
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
20
|
-
from fractal_server.app.routes.auth import
|
|
20
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
21
21
|
from fractal_server.app.schemas.v2 import ResourceType
|
|
22
22
|
from fractal_server.app.schemas.v2 import TaskCollectCustomV2
|
|
23
23
|
from fractal_server.app.schemas.v2 import TaskCreateV2
|
|
@@ -45,7 +45,7 @@ async def collect_task_custom(
|
|
|
45
45
|
task_collect: TaskCollectCustomV2,
|
|
46
46
|
private: bool = False,
|
|
47
47
|
user_group_id: int | None = None,
|
|
48
|
-
user: UserOAuth = Depends(
|
|
48
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
49
49
|
db: AsyncSession = Depends(get_async_db),
|
|
50
50
|
) -> list[TaskReadV2]:
|
|
51
51
|
# Get validated resource and profile
|
|
@@ -156,6 +156,7 @@ async def collect_task_custom(
|
|
|
156
156
|
user_id=user.id,
|
|
157
157
|
user_group_id=user_group_id,
|
|
158
158
|
version=task_collect.version,
|
|
159
|
+
resource_id=resource_id,
|
|
159
160
|
)
|
|
160
161
|
TaskGroupCreateV2(**task_group_attrs)
|
|
161
162
|
|
|
@@ -173,7 +174,7 @@ async def collect_task_custom(
|
|
|
173
174
|
db=db,
|
|
174
175
|
)
|
|
175
176
|
|
|
176
|
-
task_group = TaskGroupV2(**task_group_attrs
|
|
177
|
+
task_group = TaskGroupV2(**task_group_attrs)
|
|
177
178
|
db.add(task_group)
|
|
178
179
|
await db.commit()
|
|
179
180
|
await db.refresh(task_group)
|
|
@@ -28,7 +28,7 @@ from fractal_server.app.routes.api.v2._aux_functions_tasks import (
|
|
|
28
28
|
from fractal_server.app.routes.api.v2._aux_functions_tasks import (
|
|
29
29
|
_verify_non_duplication_user_constraint,
|
|
30
30
|
)
|
|
31
|
-
from fractal_server.app.routes.auth import
|
|
31
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
32
32
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
33
33
|
validate_user_profile,
|
|
34
34
|
)
|
|
@@ -85,7 +85,7 @@ async def collect_task_pixi(
|
|
|
85
85
|
pixi_version: NonEmptyStr | None = Form(None),
|
|
86
86
|
private: bool = False,
|
|
87
87
|
user_group_id: int | None = None,
|
|
88
|
-
user: UserOAuth = Depends(
|
|
88
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
89
89
|
db: AsyncSession = Depends(get_async_db),
|
|
90
90
|
) -> TaskGroupActivityV2Read:
|
|
91
91
|
# Get validated resource and profile
|
|
@@ -21,7 +21,7 @@ from fractal_server.app.models import LinkUserGroup
|
|
|
21
21
|
from fractal_server.app.models import UserOAuth
|
|
22
22
|
from fractal_server.app.models.v2 import TaskGroupActivityV2
|
|
23
23
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
24
|
-
from fractal_server.app.routes.auth import
|
|
24
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
25
25
|
from fractal_server.app.routes.auth._aux_auth import _get_default_usergroup_id
|
|
26
26
|
from fractal_server.app.routes.auth._aux_auth import (
|
|
27
27
|
_verify_user_belongs_to_group,
|
|
@@ -66,7 +66,7 @@ async def get_task_group_activity_list(
|
|
|
66
66
|
status: TaskGroupActivityStatusV2 | None = None,
|
|
67
67
|
action: TaskGroupActivityActionV2 | None = None,
|
|
68
68
|
timestamp_started_min: AwareDatetime | None = None,
|
|
69
|
-
user: UserOAuth = Depends(
|
|
69
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
70
70
|
db: AsyncSession = Depends(get_async_db),
|
|
71
71
|
) -> list[TaskGroupActivityV2Read]:
|
|
72
72
|
stm = select(TaskGroupActivityV2).where(
|
|
@@ -98,7 +98,7 @@ async def get_task_group_activity_list(
|
|
|
98
98
|
)
|
|
99
99
|
async def get_task_group_activity(
|
|
100
100
|
task_group_activity_id: int,
|
|
101
|
-
user: UserOAuth = Depends(
|
|
101
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
102
102
|
db: AsyncSession = Depends(get_async_db),
|
|
103
103
|
) -> TaskGroupActivityV2Read:
|
|
104
104
|
activity = await db.get(TaskGroupActivityV2, task_group_activity_id)
|
|
@@ -122,7 +122,7 @@ async def get_task_group_activity(
|
|
|
122
122
|
|
|
123
123
|
@router.get("/", response_model=list[tuple[str, list[TaskGroupReadV2]]])
|
|
124
124
|
async def get_task_group_list(
|
|
125
|
-
user: UserOAuth = Depends(
|
|
125
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
126
126
|
db: AsyncSession = Depends(get_async_db),
|
|
127
127
|
only_active: bool = False,
|
|
128
128
|
only_owner: bool = False,
|
|
@@ -182,7 +182,7 @@ async def get_task_group_list(
|
|
|
182
182
|
@router.get("/{task_group_id}/", response_model=TaskGroupReadV2)
|
|
183
183
|
async def get_task_group(
|
|
184
184
|
task_group_id: int,
|
|
185
|
-
user: UserOAuth = Depends(
|
|
185
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
186
186
|
db: AsyncSession = Depends(get_async_db),
|
|
187
187
|
) -> TaskGroupReadV2:
|
|
188
188
|
"""
|
|
@@ -200,7 +200,7 @@ async def get_task_group(
|
|
|
200
200
|
async def patch_task_group(
|
|
201
201
|
task_group_id: int,
|
|
202
202
|
task_group_update: TaskGroupUpdateV2,
|
|
203
|
-
user: UserOAuth = Depends(
|
|
203
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
204
204
|
db: AsyncSession = Depends(get_async_db),
|
|
205
205
|
) -> TaskGroupReadV2:
|
|
206
206
|
"""
|
|
@@ -13,7 +13,7 @@ from fractal_server.app.db import AsyncSession
|
|
|
13
13
|
from fractal_server.app.db import get_async_db
|
|
14
14
|
from fractal_server.app.models import UserOAuth
|
|
15
15
|
from fractal_server.app.models.v2 import TaskGroupActivityV2
|
|
16
|
-
from fractal_server.app.routes.auth import
|
|
16
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
17
17
|
from fractal_server.app.routes.aux.validate_user_profile import (
|
|
18
18
|
validate_user_profile,
|
|
19
19
|
)
|
|
@@ -50,7 +50,7 @@ async def deactivate_task_group(
|
|
|
50
50
|
task_group_id: int,
|
|
51
51
|
background_tasks: BackgroundTasks,
|
|
52
52
|
response: Response,
|
|
53
|
-
user: UserOAuth = Depends(
|
|
53
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
54
54
|
db: AsyncSession = Depends(get_async_db),
|
|
55
55
|
) -> TaskGroupActivityV2Read:
|
|
56
56
|
"""
|
|
@@ -154,7 +154,7 @@ async def reactivate_task_group(
|
|
|
154
154
|
task_group_id: int,
|
|
155
155
|
background_tasks: BackgroundTasks,
|
|
156
156
|
response: Response,
|
|
157
|
-
user: UserOAuth = Depends(
|
|
157
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
158
158
|
db: AsyncSession = Depends(get_async_db),
|
|
159
159
|
) -> TaskGroupReadV2:
|
|
160
160
|
"""
|
|
@@ -263,7 +263,7 @@ async def delete_task_group(
|
|
|
263
263
|
task_group_id: int,
|
|
264
264
|
background_tasks: BackgroundTasks,
|
|
265
265
|
response: Response,
|
|
266
|
-
user: UserOAuth = Depends(
|
|
266
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
267
267
|
db: AsyncSession = Depends(get_async_db),
|
|
268
268
|
) -> TaskGroupActivityV2Read:
|
|
269
269
|
"""
|
|
@@ -23,7 +23,7 @@ from ._aux_functions_tasks import _get_task_group_or_404
|
|
|
23
23
|
from ._aux_functions_tasks import _get_task_read_access
|
|
24
24
|
from fractal_server.app.models import UserOAuth
|
|
25
25
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
26
|
-
from fractal_server.app.routes.auth import
|
|
26
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
27
27
|
from fractal_server.app.schemas.v2 import TaskType
|
|
28
28
|
from fractal_server.app.schemas.v2 import WorkflowTaskReadV2
|
|
29
29
|
from fractal_server.app.schemas.v2 import WorkflowTaskReplaceV2
|
|
@@ -75,7 +75,7 @@ class TaskVersionRead(BaseModel):
|
|
|
75
75
|
async def get_workflow_version_update_candidates(
|
|
76
76
|
project_id: int,
|
|
77
77
|
workflow_id: int,
|
|
78
|
-
user: UserOAuth = Depends(
|
|
78
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
79
79
|
db: AsyncSession = Depends(get_async_db),
|
|
80
80
|
) -> list[list[TaskVersionRead]]:
|
|
81
81
|
workflow = await _get_workflow_check_owner(
|
|
@@ -177,7 +177,7 @@ async def replace_workflowtask(
|
|
|
177
177
|
workflow_task_id: int,
|
|
178
178
|
task_id: int,
|
|
179
179
|
replace: WorkflowTaskReplaceV2,
|
|
180
|
-
user: UserOAuth = Depends(
|
|
180
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
181
181
|
db: AsyncSession = Depends(get_async_db),
|
|
182
182
|
) -> WorkflowTaskReadV2:
|
|
183
183
|
# Get objects from database
|
|
@@ -26,7 +26,7 @@ from ._aux_functions import _workflow_has_submitted_job
|
|
|
26
26
|
from ._aux_functions_tasks import _add_warnings_to_workflow_tasks
|
|
27
27
|
from fractal_server.app.models import UserOAuth
|
|
28
28
|
from fractal_server.app.models.v2 import TaskGroupV2
|
|
29
|
-
from fractal_server.app.routes.auth import
|
|
29
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
30
30
|
from fractal_server.images.tools import merge_type_filters
|
|
31
31
|
|
|
32
32
|
router = APIRouter()
|
|
@@ -38,7 +38,7 @@ router = APIRouter()
|
|
|
38
38
|
)
|
|
39
39
|
async def get_workflow_list(
|
|
40
40
|
project_id: int,
|
|
41
|
-
user: UserOAuth = Depends(
|
|
41
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
42
42
|
db: AsyncSession = Depends(get_async_db),
|
|
43
43
|
) -> list[WorkflowReadV2] | None:
|
|
44
44
|
"""
|
|
@@ -65,7 +65,7 @@ async def get_workflow_list(
|
|
|
65
65
|
async def create_workflow(
|
|
66
66
|
project_id: int,
|
|
67
67
|
workflow: WorkflowCreateV2,
|
|
68
|
-
user: UserOAuth = Depends(
|
|
68
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
69
69
|
db: AsyncSession = Depends(get_async_db),
|
|
70
70
|
) -> WorkflowReadV2 | None:
|
|
71
71
|
"""
|
|
@@ -93,7 +93,7 @@ async def create_workflow(
|
|
|
93
93
|
async def read_workflow(
|
|
94
94
|
project_id: int,
|
|
95
95
|
workflow_id: int,
|
|
96
|
-
user: UserOAuth = Depends(
|
|
96
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
97
97
|
db: AsyncSession = Depends(get_async_db),
|
|
98
98
|
) -> WorkflowReadV2WithWarnings | None:
|
|
99
99
|
"""
|
|
@@ -127,7 +127,7 @@ async def update_workflow(
|
|
|
127
127
|
project_id: int,
|
|
128
128
|
workflow_id: int,
|
|
129
129
|
patch: WorkflowUpdateV2,
|
|
130
|
-
user: UserOAuth = Depends(
|
|
130
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
131
131
|
db: AsyncSession = Depends(get_async_db),
|
|
132
132
|
) -> WorkflowReadV2WithWarnings | None:
|
|
133
133
|
"""
|
|
@@ -201,7 +201,7 @@ async def update_workflow(
|
|
|
201
201
|
async def delete_workflow(
|
|
202
202
|
project_id: int,
|
|
203
203
|
workflow_id: int,
|
|
204
|
-
user: UserOAuth = Depends(
|
|
204
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
205
205
|
db: AsyncSession = Depends(get_async_db),
|
|
206
206
|
) -> Response:
|
|
207
207
|
"""
|
|
@@ -246,7 +246,7 @@ async def delete_workflow(
|
|
|
246
246
|
async def export_workflow(
|
|
247
247
|
project_id: int,
|
|
248
248
|
workflow_id: int,
|
|
249
|
-
user: UserOAuth = Depends(
|
|
249
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
250
250
|
db: AsyncSession = Depends(get_async_db),
|
|
251
251
|
) -> WorkflowExportV2 | None:
|
|
252
252
|
"""
|
|
@@ -277,7 +277,7 @@ async def export_workflow(
|
|
|
277
277
|
|
|
278
278
|
@router.get("/workflow/", response_model=list[WorkflowReadV2])
|
|
279
279
|
async def get_user_workflows(
|
|
280
|
-
user: UserOAuth = Depends(
|
|
280
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
281
281
|
db: AsyncSession = Depends(get_async_db),
|
|
282
282
|
) -> list[WorkflowReadV2]:
|
|
283
283
|
"""
|
|
@@ -303,7 +303,7 @@ class WorkflowTaskTypeFiltersInfo(BaseModel):
|
|
|
303
303
|
async def get_workflow_type_filters(
|
|
304
304
|
project_id: int,
|
|
305
305
|
workflow_id: int,
|
|
306
|
-
user: UserOAuth = Depends(
|
|
306
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
307
307
|
db: AsyncSession = Depends(get_async_db),
|
|
308
308
|
) -> list[WorkflowTaskTypeFiltersInfo]:
|
|
309
309
|
"""
|
|
@@ -24,7 +24,7 @@ from fractal_server.app.models.v2 import TaskGroupV2
|
|
|
24
24
|
from fractal_server.app.routes.api.v2._aux_task_group_disambiguation import (
|
|
25
25
|
_disambiguate_task_groups,
|
|
26
26
|
)
|
|
27
|
-
from fractal_server.app.routes.auth import
|
|
27
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
28
28
|
from fractal_server.app.routes.auth._aux_auth import _get_default_usergroup_id
|
|
29
29
|
from fractal_server.app.schemas.v2 import TaskImportV2
|
|
30
30
|
from fractal_server.logger import set_logger
|
|
@@ -205,7 +205,7 @@ async def _get_task_by_taskimport(
|
|
|
205
205
|
async def import_workflow(
|
|
206
206
|
project_id: int,
|
|
207
207
|
workflow_import: WorkflowImportV2,
|
|
208
|
-
user: UserOAuth = Depends(
|
|
208
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
209
209
|
db: AsyncSession = Depends(get_async_db),
|
|
210
210
|
) -> WorkflowReadV2WithWarnings:
|
|
211
211
|
"""
|
|
@@ -15,7 +15,7 @@ from ._aux_functions import _workflow_insert_task
|
|
|
15
15
|
from ._aux_functions_tasks import _check_type_filters_compatibility
|
|
16
16
|
from ._aux_functions_tasks import _get_task_read_access
|
|
17
17
|
from fractal_server.app.models import UserOAuth
|
|
18
|
-
from fractal_server.app.routes.auth import
|
|
18
|
+
from fractal_server.app.routes.auth import current_user_act_ver_prof
|
|
19
19
|
from fractal_server.app.schemas.v2 import TaskType
|
|
20
20
|
from fractal_server.app.schemas.v2 import WorkflowTaskCreateV2
|
|
21
21
|
from fractal_server.app.schemas.v2 import WorkflowTaskReadV2
|
|
@@ -34,7 +34,7 @@ async def create_workflowtask(
|
|
|
34
34
|
workflow_id: int,
|
|
35
35
|
task_id: int,
|
|
36
36
|
wftask: WorkflowTaskCreateV2,
|
|
37
|
-
user: UserOAuth = Depends(
|
|
37
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
38
38
|
db: AsyncSession = Depends(get_async_db),
|
|
39
39
|
) -> WorkflowTaskReadV2 | None:
|
|
40
40
|
"""
|
|
@@ -103,7 +103,7 @@ async def read_workflowtask(
|
|
|
103
103
|
project_id: int,
|
|
104
104
|
workflow_id: int,
|
|
105
105
|
workflow_task_id: int,
|
|
106
|
-
user: UserOAuth = Depends(
|
|
106
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
107
107
|
db: AsyncSession = Depends(get_async_db),
|
|
108
108
|
):
|
|
109
109
|
workflow_task, _ = await _get_workflow_task_check_owner(
|
|
@@ -125,7 +125,7 @@ async def update_workflowtask(
|
|
|
125
125
|
workflow_id: int,
|
|
126
126
|
workflow_task_id: int,
|
|
127
127
|
workflow_task_update: WorkflowTaskUpdateV2,
|
|
128
|
-
user: UserOAuth = Depends(
|
|
128
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
129
129
|
db: AsyncSession = Depends(get_async_db),
|
|
130
130
|
) -> WorkflowTaskReadV2 | None:
|
|
131
131
|
"""
|
|
@@ -210,7 +210,7 @@ async def delete_workflowtask(
|
|
|
210
210
|
project_id: int,
|
|
211
211
|
workflow_id: int,
|
|
212
212
|
workflow_task_id: int,
|
|
213
|
-
user: UserOAuth = Depends(
|
|
213
|
+
user: UserOAuth = Depends(current_user_act_ver_prof),
|
|
214
214
|
db: AsyncSession = Depends(get_async_db),
|
|
215
215
|
) -> Response:
|
|
216
216
|
"""
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
from fastapi import Depends
|
|
2
|
+
from fastapi import HTTPException
|
|
3
|
+
from fastapi import status
|
|
1
4
|
from fastapi_users import FastAPIUsers
|
|
2
5
|
from fastapi_users.authentication import AuthenticationBackend
|
|
3
6
|
from fastapi_users.authentication import BearerTransport
|
|
@@ -46,10 +49,36 @@ fastapi_users = FastAPIUsers[UserOAuth, int](
|
|
|
46
49
|
get_user_manager,
|
|
47
50
|
[token_backend, cookie_backend],
|
|
48
51
|
)
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
+
|
|
53
|
+
# Current-user dependencies
|
|
54
|
+
current_user_act = fastapi_users.current_user(active=True)
|
|
55
|
+
current_user_act_ver = fastapi_users.current_user(
|
|
56
|
+
active=True,
|
|
57
|
+
verified=True,
|
|
52
58
|
)
|
|
53
|
-
|
|
54
|
-
|
|
59
|
+
|
|
60
|
+
|
|
61
|
+
async def current_user_act_ver_prof(
|
|
62
|
+
user: UserOAuth = Depends(current_user_act_ver),
|
|
63
|
+
) -> UserOAuth:
|
|
64
|
+
"""
|
|
65
|
+
Require a active&verified user, with a non-null `profile_id`.
|
|
66
|
+
|
|
67
|
+
Raises 401 if user does not exist or is not active.
|
|
68
|
+
Raises 403 if user is not verified or has null `profile_id`.
|
|
69
|
+
"""
|
|
70
|
+
if user.profile_id is None:
|
|
71
|
+
raise HTTPException(
|
|
72
|
+
status_code=status.HTTP_403_FORBIDDEN,
|
|
73
|
+
detail=(
|
|
74
|
+
f"Forbidden access "
|
|
75
|
+
f"({user.is_verified=} {user.profile_id=})."
|
|
76
|
+
),
|
|
77
|
+
)
|
|
78
|
+
return user
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
current_superuser_act = fastapi_users.current_user(
|
|
82
|
+
active=True,
|
|
83
|
+
superuser=True,
|
|
55
84
|
)
|