fractal-server 2.17.0a4__py3-none-any.whl → 2.17.0a6__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.
Files changed (67) hide show
  1. fractal_server/__init__.py +1 -1
  2. fractal_server/__main__.py +22 -26
  3. fractal_server/app/models/security.py +19 -21
  4. fractal_server/app/models/user_settings.py +1 -0
  5. fractal_server/app/models/v2/task_group.py +1 -0
  6. fractal_server/app/routes/admin/v2/accounting.py +3 -3
  7. fractal_server/app/routes/admin/v2/impersonate.py +2 -2
  8. fractal_server/app/routes/admin/v2/job.py +6 -6
  9. fractal_server/app/routes/admin/v2/profile.py +18 -4
  10. fractal_server/app/routes/admin/v2/project.py +2 -2
  11. fractal_server/app/routes/admin/v2/resource.py +8 -8
  12. fractal_server/app/routes/admin/v2/task.py +11 -2
  13. fractal_server/app/routes/admin/v2/task_group.py +16 -12
  14. fractal_server/app/routes/admin/v2/task_group_lifecycle.py +4 -4
  15. fractal_server/app/routes/api/__init__.py +14 -5
  16. fractal_server/app/routes/api/v2/dataset.py +10 -19
  17. fractal_server/app/routes/api/v2/history.py +8 -8
  18. fractal_server/app/routes/api/v2/images.py +5 -5
  19. fractal_server/app/routes/api/v2/job.py +8 -8
  20. fractal_server/app/routes/api/v2/pre_submission_checks.py +3 -3
  21. fractal_server/app/routes/api/v2/project.py +6 -6
  22. fractal_server/app/routes/api/v2/status_legacy.py +2 -2
  23. fractal_server/app/routes/api/v2/submit.py +25 -29
  24. fractal_server/app/routes/api/v2/task.py +6 -7
  25. fractal_server/app/routes/api/v2/task_collection.py +4 -3
  26. fractal_server/app/routes/api/v2/task_collection_custom.py +4 -3
  27. fractal_server/app/routes/api/v2/task_collection_pixi.py +2 -2
  28. fractal_server/app/routes/api/v2/task_group.py +6 -6
  29. fractal_server/app/routes/api/v2/task_group_lifecycle.py +4 -4
  30. fractal_server/app/routes/api/v2/task_version_update.py +3 -3
  31. fractal_server/app/routes/api/v2/workflow.py +9 -9
  32. fractal_server/app/routes/api/v2/workflow_import.py +2 -2
  33. fractal_server/app/routes/api/v2/workflowtask.py +5 -5
  34. fractal_server/app/routes/auth/__init__.py +34 -5
  35. fractal_server/app/routes/auth/current_user.py +22 -72
  36. fractal_server/app/routes/auth/group.py +8 -35
  37. fractal_server/app/routes/auth/oauth.py +1 -1
  38. fractal_server/app/routes/auth/register.py +2 -2
  39. fractal_server/app/routes/auth/users.py +6 -48
  40. fractal_server/app/schemas/__init__.py +0 -1
  41. fractal_server/app/schemas/user.py +23 -0
  42. fractal_server/app/schemas/v2/__init__.py +1 -0
  43. fractal_server/app/schemas/v2/task_group.py +5 -0
  44. fractal_server/app/security/__init__.py +134 -46
  45. fractal_server/app/security/signup_email.py +52 -34
  46. fractal_server/config/__init__.py +6 -0
  47. fractal_server/config/_data.py +68 -0
  48. fractal_server/config/_email.py +10 -47
  49. fractal_server/config/_main.py +3 -56
  50. fractal_server/config/_oauth.py +2 -2
  51. fractal_server/main.py +3 -2
  52. fractal_server/migrations/versions/f65ee53991e3_user_settings_related.py +67 -0
  53. fractal_server/runner/executors/slurm_common/base_slurm_runner.py +1 -1
  54. fractal_server/runner/executors/slurm_common/slurm_config.py +5 -8
  55. fractal_server/runner/executors/slurm_ssh/runner.py +1 -1
  56. fractal_server/runner/executors/slurm_sudo/runner.py +1 -1
  57. fractal_server/runner/v2/_slurm_ssh.py +2 -1
  58. fractal_server/runner/v2/_slurm_sudo.py +1 -1
  59. fractal_server/runner/v2/submit_workflow.py +12 -12
  60. {fractal_server-2.17.0a4.dist-info → fractal_server-2.17.0a6.dist-info}/METADATA +4 -6
  61. {fractal_server-2.17.0a4.dist-info → fractal_server-2.17.0a6.dist-info}/RECORD +64 -65
  62. fractal_server/app/routes/aux/validate_user_settings.py +0 -76
  63. fractal_server/app/schemas/user_settings.py +0 -63
  64. fractal_server/app/user_settings.py +0 -32
  65. {fractal_server-2.17.0a4.dist-info → fractal_server-2.17.0a6.dist-info}/WHEEL +0 -0
  66. {fractal_server-2.17.0a4.dist-info → fractal_server-2.17.0a6.dist-info}/entry_points.txt +0 -0
  67. {fractal_server-2.17.0a4.dist-info → fractal_server-2.17.0a6.dist-info}/licenses/LICENSE +0 -0
@@ -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 current_active_verified_user
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(current_active_verified_user),
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, resource_id=resource_id)
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 current_active_verified_user
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(current_active_verified_user),
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 current_active_user
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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 current_active_user
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(current_active_user),
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(current_active_user),
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(current_active_user),
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 current_active_user
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(current_active_user),
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(current_active_user),
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 current_active_user
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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 current_active_user
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(current_active_user),
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 current_active_user
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(current_active_user),
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(current_active_user),
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(current_active_user),
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(current_active_user),
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
- current_active_user = fastapi_users.current_user(active=True)
50
- current_active_verified_user = fastapi_users.current_user(
51
- active=True, verified=True
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
- current_active_superuser = fastapi_users.current_user(
54
- active=True, superuser=True
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
  )
@@ -5,7 +5,6 @@ import os
5
5
 
6
6
  from fastapi import APIRouter
7
7
  from fastapi import Depends
8
- from fastapi_users import schemas
9
8
  from sqlalchemy.ext.asyncio import AsyncSession
10
9
  from sqlmodel import select
11
10
 
@@ -15,23 +14,18 @@ from fractal_server.app.models import Profile
15
14
  from fractal_server.app.models import Resource
16
15
  from fractal_server.app.models import UserGroup
17
16
  from fractal_server.app.models import UserOAuth
18
- from fractal_server.app.models import UserSettings
19
- from fractal_server.app.routes.auth import current_active_user
17
+ from fractal_server.app.routes.auth import current_user_act
20
18
  from fractal_server.app.routes.auth._aux_auth import (
21
19
  _get_single_user_with_groups,
22
20
  )
23
- from fractal_server.app.routes.aux.validate_user_settings import (
24
- verify_user_has_settings,
25
- )
26
21
  from fractal_server.app.schemas import UserProfileInfo
27
- from fractal_server.app.schemas import UserSettingsReadStrict
28
- from fractal_server.app.schemas import UserSettingsUpdateStrict
29
22
  from fractal_server.app.schemas.user import UserRead
30
23
  from fractal_server.app.schemas.user import UserUpdate
31
24
  from fractal_server.app.schemas.user import UserUpdateStrict
32
25
  from fractal_server.app.security import get_user_manager
33
26
  from fractal_server.app.security import UserManager
34
- from fractal_server.config import get_settings
27
+ from fractal_server.config import DataAuthScheme
28
+ from fractal_server.config import get_data_settings
35
29
  from fractal_server.syringe import Inject
36
30
 
37
31
  router_current_user = APIRouter()
@@ -40,7 +34,7 @@ router_current_user = APIRouter()
40
34
  @router_current_user.get("/current-user/", response_model=UserRead)
41
35
  async def get_current_user(
42
36
  group_ids_names: bool = False,
43
- user: UserOAuth = Depends(current_active_user),
37
+ user: UserOAuth = Depends(current_user_act),
44
38
  db: AsyncSession = Depends(get_async_db),
45
39
  ):
46
40
  """
@@ -56,7 +50,7 @@ async def get_current_user(
56
50
  @router_current_user.patch("/current-user/", response_model=UserRead)
57
51
  async def patch_current_user(
58
52
  user_update: UserUpdateStrict,
59
- current_user: UserOAuth = Depends(current_active_user),
53
+ current_user: UserOAuth = Depends(current_user_act),
60
54
  user_manager: UserManager = Depends(get_user_manager),
61
55
  db: AsyncSession = Depends(get_async_db),
62
56
  ):
@@ -71,7 +65,7 @@ async def patch_current_user(
71
65
  # their own password
72
66
 
73
67
  user = await user_manager.update(update, current_user, safe=True)
74
- validated_user = schemas.model_validate(UserOAuth, user.model_dump())
68
+ validated_user = UserOAuth.model_validate(user.model_dump())
75
69
 
76
70
  patched_user = await db.get(
77
71
  UserOAuth, validated_user.id, populate_existing=True
@@ -82,47 +76,12 @@ async def patch_current_user(
82
76
  return patched_user_with_groups
83
77
 
84
78
 
85
- @router_current_user.get(
86
- "/current-user/settings/", response_model=UserSettingsReadStrict
87
- )
88
- async def get_current_user_settings(
89
- current_user: UserOAuth = Depends(current_active_user),
90
- db: AsyncSession = Depends(get_async_db),
91
- ) -> UserSettingsReadStrict:
92
- verify_user_has_settings(current_user)
93
- user_settings = await db.get(UserSettings, current_user.user_settings_id)
94
- return user_settings
95
-
96
-
97
- @router_current_user.patch(
98
- "/current-user/settings/", response_model=UserSettingsReadStrict
99
- )
100
- async def patch_current_user_settings(
101
- settings_update: UserSettingsUpdateStrict,
102
- current_user: UserOAuth = Depends(current_active_user),
103
- db: AsyncSession = Depends(get_async_db),
104
- ) -> UserSettingsReadStrict:
105
- verify_user_has_settings(current_user)
106
- current_user_settings = await db.get(
107
- UserSettings, current_user.user_settings_id
108
- )
109
-
110
- for k, v in settings_update.model_dump(exclude_unset=True).items():
111
- setattr(current_user_settings, k, v)
112
-
113
- db.add(current_user_settings)
114
- await db.commit()
115
- await db.refresh(current_user_settings)
116
-
117
- return current_user_settings
118
-
119
-
120
79
  @router_current_user.get(
121
80
  "/current-user/profile-info/",
122
81
  response_model=UserProfileInfo,
123
82
  )
124
83
  async def get_current_user_profile_info(
125
- current_user: UserOAuth = Depends(current_active_user),
84
+ current_user: UserOAuth = Depends(current_user_act),
126
85
  db: AsyncSession = Depends(get_async_db),
127
86
  ) -> UserProfileInfo:
128
87
  stm = (
@@ -152,45 +111,37 @@ async def get_current_user_profile_info(
152
111
  "/current-user/allowed-viewer-paths/", response_model=list[str]
153
112
  )
154
113
  async def get_current_user_allowed_viewer_paths(
155
- current_user: UserOAuth = Depends(current_active_user),
114
+ current_user: UserOAuth = Depends(current_user_act),
156
115
  db: AsyncSession = Depends(get_async_db),
157
116
  ) -> list[str]:
158
117
  """
159
118
  Returns the allowed viewer paths for current user, according to the
160
- selected FRACTAL_VIEWER_AUTHORIZATION_SCHEME
119
+ selected FRACTAL_DATA_AUTH_SCHEME
161
120
  """
162
121
 
163
- settings = Inject(get_settings)
164
-
165
- if settings.FRACTAL_VIEWER_AUTHORIZATION_SCHEME == "none":
166
- return []
122
+ data_settings = Inject(get_data_settings)
167
123
 
168
124
  authorized_paths = []
169
125
 
170
- # Respond with 422 error if user has no settings
171
- verify_user_has_settings(current_user)
126
+ if data_settings.FRACTAL_DATA_AUTH_SCHEME == DataAuthScheme.NONE:
127
+ return authorized_paths
172
128
 
173
- # Load current user settings
174
- current_user_settings = await db.get(
175
- UserSettings, current_user.user_settings_id
176
- )
177
- # If project_dir is set, append it to the list of authorized paths
178
- if current_user_settings.project_dir is not None:
179
- authorized_paths.append(current_user_settings.project_dir)
129
+ # Append `project_dir` to the list of authorized paths
130
+ authorized_paths.append(current_user.project_dir)
180
131
 
181
132
  # If auth scheme is "users-folders" and `slurm_user` is set,
182
133
  # build and append the user folder
183
134
  if (
184
- settings.FRACTAL_VIEWER_AUTHORIZATION_SCHEME == "users-folders"
185
- and current_user_settings.slurm_user is not None
135
+ data_settings.FRACTAL_DATA_AUTH_SCHEME == DataAuthScheme.USERS_FOLDERS
136
+ and current_user.profile_id is not None
186
137
  ):
187
- base_folder = settings.FRACTAL_VIEWER_BASE_FOLDER
188
- user_folder = os.path.join(
189
- base_folder, current_user_settings.slurm_user
190
- )
191
- authorized_paths.append(user_folder)
138
+ profile = await db.get(Profile, current_user.profile_id)
139
+ if profile is not None and profile.username is not None:
140
+ base_folder = data_settings.FRACTAL_DATA_BASE_FOLDER
141
+ user_folder = os.path.join(base_folder, profile.username)
142
+ authorized_paths.append(user_folder)
192
143
 
193
- if settings.FRACTAL_VIEWER_AUTHORIZATION_SCHEME == "viewer-paths":
144
+ if data_settings.FRACTAL_DATA_AUTH_SCHEME == DataAuthScheme.VIEWER_PATHS:
194
145
  # Returns the union of `viewer_paths` for all user's groups
195
146
  cmd = (
196
147
  select(UserGroup.viewer_paths)
@@ -207,7 +158,6 @@ async def get_current_user_allowed_viewer_paths(
207
158
  for _viewer_paths in viewer_paths_nested
208
159
  for path in _viewer_paths
209
160
  }
210
-
211
161
  authorized_paths.extend(all_viewer_paths_set)
212
162
 
213
163
  return authorized_paths
@@ -9,7 +9,7 @@ from fastapi import status
9
9
  from sqlalchemy.ext.asyncio import AsyncSession
10
10
  from sqlmodel import select
11
11
 
12
- from . import current_active_superuser
12
+ from . import current_superuser_act
13
13
  from ._aux_auth import _get_default_usergroup_id
14
14
  from ._aux_auth import _get_single_usergroup_with_user_ids
15
15
  from ._aux_auth import _user_or_404
@@ -18,11 +18,9 @@ from fractal_server.app.db import get_async_db
18
18
  from fractal_server.app.models import LinkUserGroup
19
19
  from fractal_server.app.models import UserGroup
20
20
  from fractal_server.app.models import UserOAuth
21
- from fractal_server.app.models import UserSettings
22
21
  from fractal_server.app.schemas.user_group import UserGroupCreate
23
22
  from fractal_server.app.schemas.user_group import UserGroupRead
24
23
  from fractal_server.app.schemas.user_group import UserGroupUpdate
25
- from fractal_server.app.schemas.user_settings import UserSettingsUpdate
26
24
  from fractal_server.app.security import FRACTAL_DEFAULT_GROUP_NAME
27
25
  from fractal_server.logger import set_logger
28
26
 
@@ -36,7 +34,7 @@ router_group = APIRouter()
36
34
  )
37
35
  async def get_list_user_groups(
38
36
  user_ids: bool = False,
39
- user: UserOAuth = Depends(current_active_superuser),
37
+ user: UserOAuth = Depends(current_superuser_act),
40
38
  db: AsyncSession = Depends(get_async_db),
41
39
  ) -> list[UserGroupRead]:
42
40
  # Get all groups
@@ -70,7 +68,7 @@ async def get_list_user_groups(
70
68
  )
71
69
  async def get_single_user_group(
72
70
  group_id: int,
73
- user: UserOAuth = Depends(current_active_superuser),
71
+ user: UserOAuth = Depends(current_superuser_act),
74
72
  db: AsyncSession = Depends(get_async_db),
75
73
  ) -> UserGroupRead:
76
74
  group = await _get_single_usergroup_with_user_ids(group_id=group_id, db=db)
@@ -84,7 +82,7 @@ async def get_single_user_group(
84
82
  )
85
83
  async def create_single_group(
86
84
  group_create: UserGroupCreate,
87
- user: UserOAuth = Depends(current_active_superuser),
85
+ user: UserOAuth = Depends(current_superuser_act),
88
86
  db: AsyncSession = Depends(get_async_db),
89
87
  ) -> UserGroupRead:
90
88
  # Check that name is not already in use
@@ -116,7 +114,7 @@ async def create_single_group(
116
114
  async def update_single_group(
117
115
  group_id: int,
118
116
  group_update: UserGroupUpdate,
119
- user: UserOAuth = Depends(current_active_superuser),
117
+ user: UserOAuth = Depends(current_superuser_act),
120
118
  db: AsyncSession = Depends(get_async_db),
121
119
  ) -> UserGroupRead:
122
120
  group = await _usergroup_or_404(group_id, db)
@@ -137,7 +135,7 @@ async def update_single_group(
137
135
  @router_group.delete("/group/{group_id}/", status_code=204)
138
136
  async def delete_single_group(
139
137
  group_id: int,
140
- user: UserOAuth = Depends(current_active_superuser),
138
+ user: UserOAuth = Depends(current_superuser_act),
141
139
  db: AsyncSession = Depends(get_async_db),
142
140
  ) -> Response:
143
141
  group = await _usergroup_or_404(group_id, db)
@@ -159,36 +157,11 @@ async def delete_single_group(
159
157
  return Response(status_code=status.HTTP_204_NO_CONTENT)
160
158
 
161
159
 
162
- @router_group.patch("/group/{group_id}/user-settings/", status_code=200)
163
- async def patch_user_settings_bulk(
164
- group_id: int,
165
- settings_update: UserSettingsUpdate,
166
- superuser: UserOAuth = Depends(current_active_superuser),
167
- db: AsyncSession = Depends(get_async_db),
168
- ):
169
- await _usergroup_or_404(group_id, db)
170
- res = await db.execute(
171
- select(UserSettings)
172
- .join(UserOAuth)
173
- .where(LinkUserGroup.user_id == UserOAuth.id)
174
- .where(LinkUserGroup.group_id == group_id)
175
- )
176
- settings_list = res.scalars().all()
177
- update = settings_update.model_dump(exclude_unset=True)
178
- for settings in settings_list:
179
- for k, v in update.items():
180
- setattr(settings, k, v)
181
- db.add(settings)
182
- await db.commit()
183
-
184
- return Response(status_code=status.HTTP_200_OK)
185
-
186
-
187
160
  @router_group.post("/group/{group_id}/add-user/{user_id}/", status_code=200)
188
161
  async def add_user_to_group(
189
162
  group_id: int,
190
163
  user_id: int,
191
- superuser: UserOAuth = Depends(current_active_superuser),
164
+ superuser: UserOAuth = Depends(current_superuser_act),
192
165
  db: AsyncSession = Depends(get_async_db),
193
166
  ) -> UserGroupRead:
194
167
  await _usergroup_or_404(group_id, db)
@@ -212,7 +185,7 @@ async def add_user_to_group(
212
185
  async def remove_user_from_group(
213
186
  group_id: int,
214
187
  user_id: int,
215
- superuser: UserOAuth = Depends(current_active_superuser),
188
+ superuser: UserOAuth = Depends(current_superuser_act),
216
189
  db: AsyncSession = Depends(get_async_db),
217
190
  ) -> UserGroupRead:
218
191
  # Check that user and group exist
@@ -29,7 +29,7 @@ def _create_client_oidc(cfg: OAuthSettings) -> OpenID:
29
29
  return OpenID(
30
30
  client_id=cfg.OAUTH_CLIENT_ID.get_secret_value(),
31
31
  client_secret=cfg.OAUTH_CLIENT_SECRET.get_secret_value(),
32
- openid_configuration_endpoint=cfg.OAUTH_OIDC_CONFIG_ENDPOINT,
32
+ openid_configuration_endpoint=cfg.OAUTH_OIDC_CONFIG_ENDPOINT.get_secret_value(), # noqa
33
33
  )
34
34
 
35
35
 
@@ -4,7 +4,7 @@ Definition of `/auth/register/` routes.
4
4
  from fastapi import APIRouter
5
5
  from fastapi import Depends
6
6
 
7
- from . import current_active_superuser
7
+ from . import current_superuser_act
8
8
  from . import fastapi_users
9
9
  from ...schemas.user import UserCreate
10
10
  from ...schemas.user import UserRead
@@ -13,7 +13,7 @@ router_register = APIRouter()
13
13
 
14
14
  router_register.include_router(
15
15
  fastapi_users.get_register_router(UserRead, UserCreate),
16
- dependencies=[Depends(current_active_superuser)],
16
+ dependencies=[Depends(current_superuser_act)],
17
17
  )
18
18
 
19
19