-
-
Notifications
You must be signed in to change notification settings - Fork 430
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
chore: unify change alias mailboxes logic
- Loading branch information
1 parent
bdb0c8b
commit 180e74d
Showing
4 changed files
with
150 additions
and
42 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,62 @@ | ||
from dataclasses import dataclass | ||
from enum import Enum | ||
from typing import List, Optional | ||
|
||
from app.db import Session | ||
from app.models import Alias, AliasMailbox, Mailbox | ||
|
||
_MAX_MAILBOXES_PER_ALIAS = 20 | ||
|
||
|
||
class CannotSetMailboxesForAliasCause(Enum): | ||
Forbidden = "Forbidden" | ||
EmptyMailboxes = "Must choose at least one mailbox" | ||
TooManyMailboxes = "Too many mailboxes" | ||
|
||
|
||
@dataclass | ||
class SetMailboxesForAliasResult: | ||
performed_change: bool | ||
reason: Optional[CannotSetMailboxesForAliasCause] | ||
|
||
|
||
def set_mailboxes_for_alias( | ||
user_id: int, alias: Alias, mailbox_ids: List[int] | ||
) -> SetMailboxesForAliasResult: | ||
if len(mailbox_ids) == 0: | ||
return SetMailboxesForAliasResult( | ||
performed_change=False, | ||
reason=CannotSetMailboxesForAliasCause.EmptyMailboxes, | ||
) | ||
if len(mailbox_ids) > _MAX_MAILBOXES_PER_ALIAS: | ||
return SetMailboxesForAliasResult( | ||
performed_change=False, | ||
reason=CannotSetMailboxesForAliasCause.TooManyMailboxes, | ||
) | ||
|
||
mailboxes = ( | ||
Session.query(Mailbox) | ||
.filter( | ||
Mailbox.id.in_(mailbox_ids), | ||
Mailbox.user_id == user_id, | ||
Mailbox.verified == True, # noqa: E712 | ||
) | ||
.all() | ||
) | ||
if len(mailboxes) != len(mailbox_ids): | ||
return SetMailboxesForAliasResult( | ||
performed_change=False, reason=CannotSetMailboxesForAliasCause.Forbidden | ||
) | ||
|
||
# first remove all existing alias-mailboxes links | ||
AliasMailbox.filter_by(alias_id=alias.id).delete() | ||
Session.flush() | ||
|
||
# then add all new mailboxes, being the first the one associated with the alias | ||
for i, mailbox in enumerate(mailboxes): | ||
if i == 0: | ||
alias.mailbox_id = mailboxes[0].id | ||
else: | ||
AliasMailbox.create(alias_id=alias.id, mailbox_id=mailbox.id) | ||
|
||
return SetMailboxesForAliasResult(performed_change=True, reason=None) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,71 @@ | ||
from typing import Tuple | ||
|
||
from app.alias_mailbox_utils import ( | ||
set_mailboxes_for_alias, | ||
CannotSetMailboxesForAliasCause, | ||
) | ||
from app.models import Alias, Mailbox, User, AliasMailbox | ||
from tests.utils import create_new_user, random_email | ||
|
||
|
||
def setup() -> Tuple[User, Alias]: | ||
user = create_new_user() | ||
alias = Alias.create( | ||
user_id=user.id, | ||
email=random_email(), | ||
mailbox_id=user.default_mailbox_id, | ||
commit=True, | ||
) | ||
return user, alias | ||
|
||
|
||
def test_set_mailboxes_for_alias_empty_list(): | ||
user, alias = setup() | ||
res = set_mailboxes_for_alias(user.id, alias, []) | ||
|
||
assert res.performed_change is False | ||
assert res.reason is CannotSetMailboxesForAliasCause.EmptyMailboxes | ||
|
||
|
||
def test_set_mailboxes_for_alias_mailbox_for_other_user(): | ||
user, alias = setup() | ||
another_user = create_new_user() | ||
res = set_mailboxes_for_alias(user.id, alias, [another_user.default_mailbox_id]) | ||
|
||
assert res.performed_change is False | ||
assert res.reason is CannotSetMailboxesForAliasCause.Forbidden | ||
|
||
|
||
def test_set_mailboxes_for_alias_mailbox_not_exists(): | ||
user, alias = setup() | ||
res = set_mailboxes_for_alias(user.id, alias, [9999999]) | ||
|
||
assert res.performed_change is False | ||
assert res.reason is CannotSetMailboxesForAliasCause.Forbidden | ||
|
||
|
||
def test_set_mailboxes_for_alias_mailbox_success(): | ||
user, alias = setup() | ||
mb1 = Mailbox.create( | ||
user_id=user.id, | ||
email=random_email(), | ||
verified=True, | ||
) | ||
mb2 = Mailbox.create( | ||
user_id=user.id, | ||
email=random_email(), | ||
verified=True, | ||
commit=True, | ||
) | ||
res = set_mailboxes_for_alias(user.id, alias, [mb1.id, mb2.id]) | ||
|
||
assert res.performed_change is True | ||
assert res.reason is None | ||
|
||
db_alias = Alias.get_by(id=alias.id) | ||
assert db_alias is not None | ||
assert db_alias.mailbox_id == mb1.id | ||
|
||
alias_mailboxes = AliasMailbox.filter_by(alias_id=alias.id).all() | ||
assert len(alias_mailboxes) == 1 | ||
assert alias_mailboxes[0].mailbox_id == mb2.id |