Skip to content

Commit

Permalink
Merge pull request #1798 from fractal-analytics-platform/1774-api-and…
Browse files Browse the repository at this point in the history
…-cascade

Settings validation and cascade deletion
  • Loading branch information
tcompa committed Sep 24, 2024
2 parents 722d7ee + 1e812b7 commit 3341841
Show file tree
Hide file tree
Showing 6 changed files with 50 additions and 7 deletions.
2 changes: 1 addition & 1 deletion fractal_server/app/models/security.py
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ class UserOAuth(SQLModel, table=True):
foreign_key="user_settings.id", default=None
)
settings: Optional[UserSettings] = Relationship(
sa_relationship_kwargs=dict(lazy="selectin")
sa_relationship_kwargs=dict(lazy="selectin", cascade="all, delete")
)

class Config:
Expand Down
4 changes: 2 additions & 2 deletions fractal_server/app/routes/aux/validate_user_settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,9 @@
from fractal_server.app.db import AsyncSession
from fractal_server.app.models import UserOAuth
from fractal_server.app.models import UserSettings
from fractal_server.app.user_settings import SlurmSshUserSettings
from fractal_server.app.user_settings import SlurmSudoUserSettings
from fractal_server.logger import set_logger
from fractal_server.user_settings import SlurmSshUserSettings
from fractal_server.user_settings import SlurmSudoUserSettings

logger = set_logger(__name__)

Expand Down
11 changes: 8 additions & 3 deletions fractal_server/app/schemas/user_settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,14 @@ class UserSettingsUpdate(BaseModel):
_slurm_user = validator("slurm_user", allow_reuse=True)(
valstr("slurm_user")
)
_slurm_accounts = validator("slurm_accounts", allow_reuse=True)(
val_unique_list("slurm_accounts")
)

@validator("slurm_accounts")
def slurm_accounts_validator(cls, value):
if value is None:
return value

Check notice on line 70 in fractal_server/app/schemas/user_settings.py

View workflow job for this annotation

GitHub Actions / Coverage

Missing coverage

Missing coverage on line 70

Check notice on line 70 in fractal_server/app/schemas/user_settings.py

View workflow job for this annotation

GitHub Actions / Coverage

Missing coverage

Missing coverage on line 70
for i, item in enumerate(value):
value[i] = valstr(f"slurm_accounts[{i}]")(item)
return val_unique_list("slurm_accounts")(value)

@validator("cache_dir")
def cache_dir_validator(cls, value):
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ class SlurmSshUserSettings(BaseModel):
ssh_private_key_path: str
ssh_tasks_dir: str
ssh_jobs_dir: str
slurm_accounts: list[str]


class SlurmSudoUserSettings(BaseModel):
Expand Down
8 changes: 7 additions & 1 deletion tests/no_version/test_auth_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -562,7 +562,7 @@ async def test_get_and_patch_user_settings(registered_superuser_client):
ssh_private_key_path="/tmp/fractal",
ssh_tasks_dir="/tmp/tasks",
# missing "ssh_jobs_dir"
# missing "slurm_user"
slurm_user="fractal",
slurm_accounts=["foo", "bar"],
cache_dir="/tmp/cache",
)
Expand All @@ -572,6 +572,12 @@ async def test_get_and_patch_user_settings(registered_superuser_client):
debug(res.json())
assert res.status_code == 200

res = await registered_superuser_client.patch(
f"{PREFIX}/users/{user_id}/settings/", json=dict(slurm_accounts=[" "])
)
debug(res.json())
assert res.status_code == 422

# Assert patch was successful
res = await registered_superuser_client.get(
f"{PREFIX}/users/{user_id}/settings/",
Expand Down
31 changes: 31 additions & 0 deletions tests/no_version/test_delete_user.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
from sqlmodel import select

from fractal_server.app.models.security import UserOAuth
from fractal_server.app.models.security import UserSettings
from fractal_server.app.models.v1 import LinkUserProject
from fractal_server.app.models.v2 import LinkUserProjectV2

Expand Down Expand Up @@ -54,3 +55,33 @@ async def test_delete_user(
assert len(project_v2.user_list) == 0
assert len(project_v1_2.user_list) == 1
assert len(project_v2_2.user_list) == 1


async def test_cascade_on_delete_user_settings(db):

user = UserOAuth(
email="user@fractal.xy",
hashed_password="fake_hashed_password",
settings=UserSettings(slurm_accounts=["account1", "account2"]),
)
db.add(user)
await db.commit()

await db.refresh(user)
user_id = user.id
user_settings_id = user.user_settings_id

await db.close()

user = await db.get(UserOAuth, user_id)
assert user is not None
user_settings = await db.get(UserSettings, user_settings_id)
assert user_settings is not None

await db.delete(user)
await db.commit()

user = await db.get(UserOAuth, user_id)
assert user is None
user_settings = await db.get(UserSettings, user_settings_id)
assert user_settings is None

0 comments on commit 3341841

Please sign in to comment.