security: enforce actor-aware Mail profile access

This commit is contained in:
2026-07-21 17:51:25 +02:00
parent 9d1d9bfb58
commit 06e0fbd3c3
7 changed files with 1336 additions and 158 deletions

View File

@@ -0,0 +1,49 @@
from __future__ import annotations
import unittest
from govoplan_mail.backend.db.models import MailMailboxFolderIndex, MailMailboxMessageIndex
from govoplan_mail.backend.mailbox_index import clear_mailbox_index
class _DeleteQuery:
def __init__(self, model: type, deleted_models: list[type]) -> None:
self.model = model
self.deleted_models = deleted_models
def filter(self, *_criteria):
return self
def delete(self, *, synchronize_session: bool) -> int:
if synchronize_session is not False:
raise AssertionError("bulk invalidation must not synchronize loaded cache rows")
self.deleted_models.append(self.model)
return 2 if self.model is MailMailboxMessageIndex else 1
class _Session:
def __init__(self) -> None:
self.deleted_models: list[type] = []
def query(self, model: type) -> _DeleteQuery:
return _DeleteQuery(model, self.deleted_models)
class MailboxIndexInvalidationTests(unittest.TestCase):
def test_profile_wide_invalidation_deletes_messages_before_folders(self) -> None:
session = _Session()
deleted_folders, deleted_messages = clear_mailbox_index(
session, # type: ignore[arg-type]
profile_id="profile-1",
)
self.assertEqual(
session.deleted_models,
[MailMailboxMessageIndex, MailMailboxFolderIndex],
)
self.assertEqual((deleted_folders, deleted_messages), (1, 2))
if __name__ == "__main__":
unittest.main()