make sure a deleted directory can't be recreated

This commit is contained in:
Son 2021-11-17 17:02:31 +01:00
parent 482aa8614c
commit 417f7b92b0
4 changed files with 109 additions and 26 deletions

View file

@ -11,6 +11,7 @@ from app.config import (
)
from app.dashboard.base import dashboard_bp
from app.db import Session
from app.errors import DirectoryInTrashError
from app.models import Directory, Mailbox, DirectoryMailbox
@ -138,33 +139,42 @@ def directory():
"warning",
)
else:
new_dir = Directory.create(
name=new_dir_name, user_id=current_user.id
)
Session.commit()
mailbox_ids = request.form.getlist("mailbox_ids")
if mailbox_ids:
# check if mailbox is not tempered with
mailboxes = []
for mailbox_id in mailbox_ids:
mailbox = Mailbox.get(mailbox_id)
if (
not mailbox
or mailbox.user_id != current_user.id
or not mailbox.verified
):
flash("Something went wrong, please retry", "warning")
return redirect(url_for("dashboard.directory"))
mailboxes.append(mailbox)
for mailbox in mailboxes:
DirectoryMailbox.create(
directory_id=new_dir.id, mailbox_id=mailbox.id
)
try:
new_dir = Directory.create(
name=new_dir_name, user_id=current_user.id
)
except DirectoryInTrashError:
flash(
f"{new_dir_name} has been used before and cannot be reused",
"error",
)
else:
Session.commit()
mailbox_ids = request.form.getlist("mailbox_ids")
if mailbox_ids:
# check if mailbox is not tempered with
mailboxes = []
for mailbox_id in mailbox_ids:
mailbox = Mailbox.get(mailbox_id)
if (
not mailbox
or mailbox.user_id != current_user.id
or not mailbox.verified
):
flash(
"Something went wrong, please retry", "warning"
)
return redirect(url_for("dashboard.directory"))
mailboxes.append(mailbox)
flash(f"Directory {new_dir.name} is created", "success")
for mailbox in mailboxes:
DirectoryMailbox.create(
directory_id=new_dir.id, mailbox_id=mailbox.id
)
Session.commit()
flash(f"Directory {new_dir.name} is created", "success")
return redirect(url_for("dashboard.directory"))

View file

@ -2,3 +2,9 @@ class AliasInTrashError(Exception):
"""raised when alias is deleted before """
pass
class DirectoryInTrashError(Exception):
"""raised when a directory is deleted before """
pass

View file

@ -32,7 +32,7 @@ from app.config import (
ALIAS_RANDOM_SUFFIX_LENGTH,
)
from app.db import Session
from app.errors import AliasInTrashError
from app.errors import AliasInTrashError, DirectoryInTrashError
from app.log import LOG
from app.oauth_models import Scope
from app.pw_models import PasswordOracle
@ -2123,6 +2123,14 @@ class Directory(Base, ModelMixin):
def nb_alias(self):
return Alias.filter_by(directory_id=self.id).count()
@classmethod
def create(cls, *args, **kwargs):
name = kwargs.get("name")
if DeletedDirectory.get_by(name=name):
raise DirectoryInTrashError
return super(Directory, cls).create(*args, **kwargs)
@classmethod
def delete(cls, obj_id):
obj: Directory = cls.get(obj_id)
@ -2133,6 +2141,7 @@ class Directory(Base, ModelMixin):
alias_utils.delete_alias(alias, user)
DeletedDirectory.create(name=obj.name)
cls.filter(cls.id == obj_id).delete()
Session.commit()

View file

@ -0,0 +1,58 @@
from flask import url_for
from app.models import Directory
from tests.utils import login
def test_create_directory(flask_client):
login(flask_client)
r = flask_client.post(
url_for("dashboard.directory"),
data={"form-name": "create", "name": "test"},
follow_redirects=True,
)
assert r.status_code == 200
assert f"Directory test is created" in r.data.decode()
assert Directory.get_by(name="test") is not None
def test_delete_directory(flask_client):
"""cannot add domain if user personal email uses this domain"""
user = login(flask_client)
directory = Directory.create(name="test", user_id=user.id, commit=True)
r = flask_client.post(
url_for("dashboard.directory"),
data={"form-name": "delete", "dir-id": directory.id},
follow_redirects=True,
)
assert r.status_code == 200
assert f"Directory test has been deleted" in r.data.decode()
assert Directory.get_by(name="test") is None
def test_create_directory_in_trash(flask_client):
user = login(flask_client)
directory = Directory.create(name="test", user_id=user.id, commit=True)
# delete the directory
r = flask_client.post(
url_for("dashboard.directory"),
data={"form-name": "delete", "dir-id": directory.id},
follow_redirects=True,
)
assert Directory.get_by(name="test") is None
# try to recreate the directory
r = flask_client.post(
url_for("dashboard.directory"),
data={"form-name": "create", "name": "test"},
follow_redirects=True,
)
assert r.status_code == 200
assert "test has been used before and cannot be reused" in r.data.decode()